├── .codacy.yml
├── .editorconfig
├── .github
├── CODEOWNERS
├── FUNDING.yml
└── workflows
│ └── gradle-build.yml
├── .gitignore
├── LICENSE
├── README.md
├── build.gradle
├── checkstyle-suppressions.xml
├── checkstyle.xml
├── gradle.properties
├── gradle
├── license.gradle
└── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
└── src
├── main
├── java
│ └── jodd
│ │ └── http
│ │ ├── Buffer.java
│ │ ├── Cookie.java
│ │ ├── HeadersMultiMap.java
│ │ ├── HttpBase.java
│ │ ├── HttpConnection.java
│ │ ├── HttpConnectionProvider.java
│ │ ├── HttpException.java
│ │ ├── HttpMultiMap.java
│ │ ├── HttpProgressListener.java
│ │ ├── HttpRequest.java
│ │ ├── HttpResponse.java
│ │ ├── HttpSession.java
│ │ ├── HttpStatus.java
│ │ ├── HttpTunnel.java
│ │ ├── HttpUtil.java
│ │ ├── ProxyInfo.java
│ │ ├── Sockets.java
│ │ ├── net
│ │ ├── HTTPProxySocketFactory.java
│ │ ├── SSLSocketHttpConnectionProvider.java
│ │ ├── SocketHttpConnection.java
│ │ ├── SocketHttpConnectionProvider.java
│ │ ├── SocketHttpSecureConnection.java
│ │ ├── Socks4ProxySocketFactory.java
│ │ ├── Socks5ProxySocketFactory.java
│ │ ├── TrustManagers.java
│ │ └── package-info.java
│ │ ├── package-info.java
│ │ └── upload
│ │ ├── ByteArrayUploadable.java
│ │ ├── FileUpload.java
│ │ ├── FileUploadFactory.java
│ │ ├── FileUploadHeader.java
│ │ ├── FileUploadable.java
│ │ ├── MultipartRequestInputStream.java
│ │ ├── MultipartStreamParser.java
│ │ ├── Uploadable.java
│ │ ├── impl
│ │ ├── AdaptiveFileUpload.java
│ │ ├── AdaptiveFileUploadFactory.java
│ │ ├── DiskFileUpload.java
│ │ ├── DiskFileUploadFactory.java
│ │ ├── MemoryFileUpload.java
│ │ ├── MemoryFileUploadFactory.java
│ │ └── package-info.java
│ │ └── package-info.java
└── resources
│ └── META-INF
│ └── LICENSE
└── test
├── java
└── jodd
│ └── http
│ ├── BufferTest.java
│ ├── CRLFInjectionTest.java
│ ├── CookieTest.java
│ ├── EchoTestServer.java
│ ├── EncodingTest.java
│ ├── FragmentTest.java
│ ├── GoogleMapsTest.java
│ ├── HttpConnectionTest.java
│ ├── HttpHeaderTest.java
│ ├── HttpMultiMapTest.java
│ ├── HttpProgressListenerTest.java
│ ├── HttpRedirectTest.java
│ ├── HttpRequestTest.java
│ ├── HttpSessionOfflineTest.java
│ ├── HttpSessionTest.java
│ ├── HttpUploadTest.java
│ ├── HttpUtilTest.java
│ ├── HttpsFactoryTest.java
│ ├── KeepAliveTest.java
│ ├── NanoHTTPD.java
│ ├── NoLocationTest.java
│ ├── ProxyTest.java
│ ├── RawTest.java
│ ├── RemoveHeaderTest.java
│ ├── TestServer.java
│ ├── TimeoutTest.java
│ ├── TomcatServer.java
│ └── fixture
│ ├── Data.java
│ ├── Echo2Servlet.java
│ ├── Echo3Servlet.java
│ ├── EchoServlet.java
│ ├── RedirectServlet.java
│ ├── SlowServlet.java
│ ├── StringHttpRequest.java
│ └── TargetServlet.java
└── resources
└── jodd
└── http
├── 1-response.txt
├── 2-response.txt
├── 3-response.txt
├── 4-response.txt
├── 5-response.txt
├── 6-response.txt
├── answer.json
└── web.xml
/.codacy.yml:
--------------------------------------------------------------------------------
1 | ---
2 | exclude_paths:
3 | - '**/test/**'
4 |
--------------------------------------------------------------------------------
/.editorconfig:
--------------------------------------------------------------------------------
1 | root = true
2 |
3 | [*]
4 | end_of_line = lf
5 | insert_final_newline = true
6 | charset = utf-8
7 |
8 | [*.java]
9 | indent_style = tab
10 |
11 | [*.js]
12 | indent_style = space
13 | indent_size = 2
14 |
15 | [*.gradle]
16 | indent_style = tab
--------------------------------------------------------------------------------
/.github/CODEOWNERS:
--------------------------------------------------------------------------------
1 | * @igr
--------------------------------------------------------------------------------
/.github/FUNDING.yml:
--------------------------------------------------------------------------------
1 | # These are supported funding model platforms
2 |
3 | github: igr
4 | patreon: igo_rs
5 |
--------------------------------------------------------------------------------
/.github/workflows/gradle-build.yml:
--------------------------------------------------------------------------------
1 | name: Build
2 |
3 | on: [push]
4 |
5 | jobs:
6 | build:
7 |
8 | runs-on: ubuntu-latest
9 | permissions:
10 | contents: read
11 | packages: write
12 | strategy:
13 | fail-fast: false
14 | matrix:
15 | jdk: [8]
16 |
17 | steps:
18 | - uses: actions/checkout@v2
19 | - name: Set up JDK 11
20 | uses: actions/setup-java@v2
21 | with:
22 | java-version: ${{ matrix.jdk }}
23 | distribution: 'temurin'
24 | server-id: github
25 | settings-path: ${{ github.workspace }}
26 |
27 | - name: Build with Gradle
28 | uses: gradle/gradle-build-action@937999e9cc2425eddc7fd62d1053baf041147db7
29 | with:
30 | arguments: build
31 |
32 | - name: Upload coverage to Codecov
33 | uses: codecov/codecov-action@v2
34 | with:
35 | file: ./build/reports/jacoco/test/jacocoTestReport.xml
36 | flags: unittests
37 | verbose: true
38 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | .idea
2 |
3 | ### Java
4 | # Compiled class file
5 | *.class
6 |
7 | # Log file
8 | *.log
9 |
10 | # BlueJ files
11 | *.ctxt
12 |
13 | # Mobile Tools for Java (J2ME)
14 | .mtj.tmp/
15 |
16 | # Package Files #
17 | *.jar
18 | *.war
19 | *.nar
20 | *.ear
21 | *.zip
22 | *.tar.gz
23 | *.rar
24 |
25 | # virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
26 | hs_err_pid*
27 |
28 | ### Gradle
29 | .gradle
30 | /build/
31 |
32 | # Ignore Gradle GUI config
33 | gradle-app.setting
34 |
35 | # Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored)
36 | !gradle-wrapper.jar
37 |
38 | # Cache of project
39 | .gradletasknamecache
40 |
41 | # # Work around https://youtrack.jetbrains.com/issue/IDEA-116898
42 | # gradle/wrapper/gradle-wrapper.properties
43 |
44 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | BSD 2-Clause License
2 |
3 | Copyright (c) 2020, Oblac
4 | All rights reserved.
5 |
6 | Redistribution and use in source and binary forms, with or without
7 | modification, are permitted provided that the following conditions are met:
8 |
9 | 1. Redistributions of source code must retain the above copyright notice, this
10 | list of conditions and the following disclaimer.
11 |
12 | 2. Redistributions in binary form must reproduce the above copyright notice,
13 | this list of conditions and the following disclaimer in the documentation
14 | and/or other materials provided with the distribution.
15 |
16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
20 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
22 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
23 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Jodd HTTP
2 |
3 | [](https://github.com/oblac/jodd)
4 | 
5 | 
6 | [](https://javadoc.io/doc/org.jodd/jodd-http)
7 | [](https://github.com/oblac/jodd-http/actions/workflows/gradle-build.yml)
8 | [](https://codecov.io/gh/oblac/jodd-http)
9 | [](https://www.codacy.com/gh/oblac/jodd-http/dashboard?utm_source=github.com&utm_medium=referral&utm_content=oblac/jodd-http&utm_campaign=Badge_Grade)
10 | [](https://stackoverflow.com/questions/tagged/jodd)
11 | [](https://github.com/oblac/jodd-http/blob/master/LICENSE)
12 |
13 | 🌟 Simple Java HTTP Client.
14 |
15 | 🏡 Website: [http.jodd.org](https://http.jodd.org)
16 |
17 | ❤️ For developers, by developer.
18 |
--------------------------------------------------------------------------------
/build.gradle:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice, this
8 | // list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright notice,
11 | // this list of conditions and the following disclaimer in the documentation
12 | // and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17 | // DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
18 | // FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19 | // DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20 | // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
21 | // CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
22 | // OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23 | // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 | // Copyright (c) 2003-present, Jodd Team (https://jodd.org)
25 |
26 | plugins {
27 | id 'java-library'
28 | id 'maven-publish'
29 | id 'jacoco'
30 | id 'signing'
31 | id 'io.codearte.nexus-staging' version '0.21.2'
32 | id 'biz.aQute.bnd.builder' version '5.2.0'
33 | }
34 |
35 | repositories {
36 | mavenCentral()
37 | mavenLocal()
38 | }
39 |
40 | group = 'org.jodd'
41 | //version = '6.0.3-SNAPSHOT'
42 | version = '6.3.0'
43 |
44 | rootProject.description = 'Jodd HTTP Client'
45 |
46 | ext {
47 | }
48 |
49 | java {
50 | sourceCompatibility = JavaVersion.VERSION_1_8
51 | targetCompatibility = JavaVersion.VERSION_1_8
52 | withSourcesJar()
53 | withJavadocJar()
54 | }
55 |
56 | dependencies {
57 | api 'org.jodd:jodd-util:6.1.+'
58 |
59 | testImplementation 'org.junit.jupiter:junit-jupiter-api:5.6.+'
60 | testImplementation 'org.junit.jupiter:junit-jupiter-params:5.6.+'
61 | testImplementation 'org.mockito:mockito-core:3.5.5'
62 | testRuntimeOnly 'org.junit.jupiter:junit-jupiter-engine:5.6.+'
63 |
64 | testImplementation 'org.apache.tomcat:tomcat-jasper:8.0.47'
65 | testImplementation 'org.apache.tomcat:tomcat-jasper-el:8.0.47'
66 | testImplementation 'org.apache.tomcat:tomcat-catalina:8.0.47'
67 | testImplementation 'org.apache.tomcat.embed:tomcat-embed-core:8.0.47'
68 | testImplementation 'org.apache.tomcat.embed:tomcat-embed-jasper:8.0.47'
69 | testImplementation 'org.apache.tomcat.embed:tomcat-embed-logging-juli:8.0.47'
70 | testImplementation 'org.apache.tomcat.embed:tomcat-embed-logging-log4j:8.0.47'
71 |
72 | testImplementation 'org.mock-server:mockserver-netty:5.2.3'
73 | }
74 |
75 | jar {
76 | bnd ('-exportcontents': 'jodd.*')
77 | manifest {
78 | attributes(
79 | 'Implementation-Title': project.name,
80 | 'Implementation-Version': project.version,
81 | 'Debug-Info': 'on',
82 | 'Built-By': 'jodd.org'
83 | )
84 | }
85 | }
86 |
87 | javadoc {
88 | options.addStringOption('Xdoclint:none', '-quiet')
89 | if (JavaVersion.current().isJava9Compatible()) {
90 | options.addBooleanOption('html5', true)
91 | }
92 | }
93 |
94 | test {
95 | useJUnitPlatform()
96 | testLogging {
97 | events "standardOut", "passed", "skipped", "failed"
98 | showExceptions true
99 | exceptionFormat "full"
100 | showCauses true
101 | showStackTraces true
102 |
103 | afterSuite { desc, result ->
104 | if (!desc.parent) { // will match the outermost suite
105 | def output = "Results: ${result.resultType} (${result.testCount} tests, ${result.successfulTestCount} successes, ${result.failedTestCount} failures, ${result.skippedTestCount} skipped)"
106 | def startItem = '| ', endItem = ' |'
107 | def repeatLength = startItem.length() + output.length() + endItem.length()
108 | println('\n' + ('-' * repeatLength) + '\n' + startItem + output + endItem + '\n' + ('-' * repeatLength))
109 | }
110 | }
111 | }
112 | jacoco {
113 | excludes += ['*Test*', '*.?', '*.fixtures.*']
114 | }
115 | }
116 |
117 | jacocoTestReport {
118 | reports {
119 | xml.enabled true
120 | csv.enabled false
121 | html.enabled true
122 | }
123 | }
124 |
125 | check.dependsOn jacocoTestReport
126 |
127 | //
128 | // PUBLISH
129 | //
130 |
131 | ext.admin = hasProperty('sonatypeUsername')
132 |
133 | publishing {
134 | publications {
135 | mavenJava(MavenPublication) {
136 | artifactId = 'jodd-http'
137 | from components.java
138 | versionMapping {
139 | usage('java-api') {
140 | fromResolutionOf('runtimeClasspath')
141 | }
142 | usage('java-runtime') {
143 | fromResolutionResult()
144 | }
145 | }
146 | pom {
147 | name = 'Jodd HTTP'
148 | description = 'Jodd HTTP Client'
149 | url = 'https://http.jodd.org'
150 | licenses {
151 | license {
152 | name = 'BSD-2-Clause'
153 | url = 'https://github.com/oblac/jodd-http/blob/master/LICENSE'
154 | }
155 | }
156 | developers {
157 | developer {
158 | id = 'igor'
159 | name = 'Igor Spasić'
160 | email = 'igor@jodd.org'
161 | timezone = '+1'
162 | }
163 | }
164 | scm {
165 | url = 'https://github.com/oblac/jodd-http.git'
166 | connection = 'scm:git:git://github.com/oblac/jodd-http.git'
167 | developerConnection = 'scm:git:ssh://git@github.com/oblac/jodd-http.git'
168 | }
169 | }
170 | }
171 | }
172 | repositories {
173 | maven {
174 | def releasesRepoUrl = "https://oss.sonatype.org/service/local/staging/deploy/maven2/"
175 | def snapshotsRepoUrl = "https://oss.sonatype.org/content/repositories/snapshots/"
176 | url = version.contains('SNAPSHOT') ? snapshotsRepoUrl : releasesRepoUrl
177 | if (admin) {
178 | credentials {
179 | username sonatypeUsername
180 | password sonatypePassword
181 | }
182 | }
183 | }
184 | }
185 | }
186 |
187 | signing {
188 | required { admin }
189 | sign publishing.publications.mavenJava
190 | }
191 |
192 | task install(dependsOn: publishToMavenLocal) {
193 | group = 'Publishing'
194 | description = 'Installs artifacts to local Maven repository'
195 | }
196 |
197 | //
198 | // RELEASE
199 | //
200 |
201 | task release() {
202 | group 'Project'
203 | description 'Rebuilds everything for the release.'
204 |
205 | dependsOn clean
206 | dependsOn build
207 | dependsOn javadoc
208 | dependsOn jacocoTestReport
209 | }
210 |
211 |
212 | //
213 | // UTILS
214 | //
215 |
216 | apply from: "${rootProject.projectDir}/gradle/license.gradle"
217 |
218 | tasks.named('wrapper') {
219 | distributionType = Wrapper.DistributionType.ALL
220 | }
221 |
222 | static def timestamp() {
223 | return new Date().format('yyyyMMddHHmmss')
224 | }
225 |
--------------------------------------------------------------------------------
/checkstyle-suppressions.xml:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/gradle.properties:
--------------------------------------------------------------------------------
1 | org.gradle.jvmargs=-Xms512M -Xmx4g -XX:MaxPermSize=1024m -XX:MaxMetaspaceSize=1g -Dkotlin.daemon.jvm.options="-Xmx1g"
2 |
--------------------------------------------------------------------------------
/gradle/license.gradle:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | task license {
27 | group 'License'
28 | description 'Check for files without a license header'
29 | doLast {
30 | license(false)
31 | }
32 | }
33 |
34 | task licenseUpdate {
35 | group 'License'
36 | description 'Updates files without a license header'
37 | doLast {
38 | license(true)
39 | }
40 | }
41 |
42 | def license(overwrite) {
43 | def headerLines = file('LICENSE').readLines()
44 |
45 | // header
46 | def doubleslashHeader = ""
47 | def doubleslashPrefix = "//"
48 | def doubleslashIsBlock = false
49 | def doubleslashStart = ""
50 | def doubleslashEnd = ""
51 | headerLines.forEach { line ->
52 | line = "// " + line
53 | doubleslashHeader += line.trim() + "\n"
54 | }
55 |
56 | // header
57 | def hashHeader = ""
58 | def hashPrefix = "#"
59 | def hashIsBlock = false
60 | def hashStart = ""
61 | def hashEnd = ""
62 | headerLines.forEach { line ->
63 | line = "# " + line
64 | hashHeader += line.trim() + "\n"
65 | }
66 |
67 | // header
68 | def tagHeader = ""
69 | def tagPrefix = ""
70 | def tagIsBlock = true
71 | def tagStart = "\n"
73 | headerLines.forEach { line ->
74 | tagHeader += line.trim() + "\n"
75 | }
76 | tagHeader = tagStart + tagHeader + tagEnd
77 |
78 |
79 | // gather sources
80 | def allSource = rootProject.sourceSets.main.allSource +
81 | rootProject.sourceSets.test.allJava
82 |
83 | allSource.files.each { file ->
84 | if (!file.name.endsWith(".java")) {
85 | return
86 | }
87 |
88 | def fileNamePath = file.absolutePath
89 | fileNamePath = fileNamePath.substring(project.rootDir.absolutePath.length() + 1)
90 |
91 | // default header, java
92 | def headerContent = doubleslashHeader
93 | def headerPrefix = doubleslashPrefix
94 | def headerIsBlock = doubleslashIsBlock
95 | def headerStart = doubleslashStart
96 | def headerEnd = doubleslashEnd
97 |
98 | // apply the license
99 | if (headerContent != null) {
100 | def fileText = file.text
101 |
102 | if (fileText.startsWith(headerContent) == false) {
103 | println(fileNamePath)
104 |
105 | if (overwrite) {
106 | // remove existing header
107 | if (headerIsBlock) {
108 | int ndx = fileText.indexOf(headerEnd)
109 | if (ndx >= 0) {
110 | fileText = fileText.substring(ndx + headerEnd.length())
111 | }
112 | } else {
113 | while (fileText.startsWith(headerPrefix)) {
114 | int ndx = fileText.indexOf("\n")
115 | fileText = fileText.substring(ndx + 1)
116 | }
117 | }
118 |
119 | // add the new header
120 | fileText = headerContent + fileText
121 |
122 | file.write(fileText)
123 | }
124 | }
125 | }
126 | }
127 | }
128 |
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/oblac/jodd-http/a07090b37b8c9c96b3c2a3411c80c0d579cefcbd/gradle/wrapper/gradle-wrapper.jar
--------------------------------------------------------------------------------
/gradle/wrapper/gradle-wrapper.properties:
--------------------------------------------------------------------------------
1 | distributionBase=GRADLE_USER_HOME
2 | distributionPath=wrapper/dists
3 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.5.1-all.zip
4 | zipStoreBase=GRADLE_USER_HOME
5 | zipStorePath=wrapper/dists
6 |
--------------------------------------------------------------------------------
/gradlew:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env sh
2 |
3 | #
4 | # Copyright 2015 the original author or authors.
5 | #
6 | # Licensed under the Apache License, Version 2.0 (the "License");
7 | # you may not use this file except in compliance with the License.
8 | # You may obtain a copy of the License at
9 | #
10 | # https://www.apache.org/licenses/LICENSE-2.0
11 | #
12 | # Unless required by applicable law or agreed to in writing, software
13 | # distributed under the License is distributed on an "AS IS" BASIS,
14 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 | # See the License for the specific language governing permissions and
16 | # limitations under the License.
17 | #
18 |
19 | ##############################################################################
20 | ##
21 | ## Gradle start up script for UN*X
22 | ##
23 | ##############################################################################
24 |
25 | # Attempt to set APP_HOME
26 | # Resolve links: $0 may be a link
27 | PRG="$0"
28 | # Need this for relative symlinks.
29 | while [ -h "$PRG" ] ; do
30 | ls=`ls -ld "$PRG"`
31 | link=`expr "$ls" : '.*-> \(.*\)$'`
32 | if expr "$link" : '/.*' > /dev/null; then
33 | PRG="$link"
34 | else
35 | PRG=`dirname "$PRG"`"/$link"
36 | fi
37 | done
38 | SAVED="`pwd`"
39 | cd "`dirname \"$PRG\"`/" >/dev/null
40 | APP_HOME="`pwd -P`"
41 | cd "$SAVED" >/dev/null
42 |
43 | APP_NAME="Gradle"
44 | APP_BASE_NAME=`basename "$0"`
45 |
46 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
47 | DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
48 |
49 | # Use the maximum available, or set MAX_FD != -1 to use that value.
50 | MAX_FD="maximum"
51 |
52 | warn () {
53 | echo "$*"
54 | }
55 |
56 | die () {
57 | echo
58 | echo "$*"
59 | echo
60 | exit 1
61 | }
62 |
63 | # OS specific support (must be 'true' or 'false').
64 | cygwin=false
65 | msys=false
66 | darwin=false
67 | nonstop=false
68 | case "`uname`" in
69 | CYGWIN* )
70 | cygwin=true
71 | ;;
72 | Darwin* )
73 | darwin=true
74 | ;;
75 | MINGW* )
76 | msys=true
77 | ;;
78 | NONSTOP* )
79 | nonstop=true
80 | ;;
81 | esac
82 |
83 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
84 |
85 | # Determine the Java command to use to start the JVM.
86 | if [ -n "$JAVA_HOME" ] ; then
87 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
88 | # IBM's JDK on AIX uses strange locations for the executables
89 | JAVACMD="$JAVA_HOME/jre/sh/java"
90 | else
91 | JAVACMD="$JAVA_HOME/bin/java"
92 | fi
93 | if [ ! -x "$JAVACMD" ] ; then
94 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
95 |
96 | Please set the JAVA_HOME variable in your environment to match the
97 | location of your Java installation."
98 | fi
99 | else
100 | JAVACMD="java"
101 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
102 |
103 | Please set the JAVA_HOME variable in your environment to match the
104 | location of your Java installation."
105 | fi
106 |
107 | # Increase the maximum file descriptors if we can.
108 | if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
109 | MAX_FD_LIMIT=`ulimit -H -n`
110 | if [ $? -eq 0 ] ; then
111 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
112 | MAX_FD="$MAX_FD_LIMIT"
113 | fi
114 | ulimit -n $MAX_FD
115 | if [ $? -ne 0 ] ; then
116 | warn "Could not set maximum file descriptor limit: $MAX_FD"
117 | fi
118 | else
119 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
120 | fi
121 | fi
122 |
123 | # For Darwin, add options to specify how the application appears in the dock
124 | if $darwin; then
125 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
126 | fi
127 |
128 | # For Cygwin or MSYS, switch paths to Windows format before running java
129 | if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then
130 | APP_HOME=`cygpath --path --mixed "$APP_HOME"`
131 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
132 | JAVACMD=`cygpath --unix "$JAVACMD"`
133 |
134 | # We build the pattern for arguments to be converted via cygpath
135 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
136 | SEP=""
137 | for dir in $ROOTDIRSRAW ; do
138 | ROOTDIRS="$ROOTDIRS$SEP$dir"
139 | SEP="|"
140 | done
141 | OURCYGPATTERN="(^($ROOTDIRS))"
142 | # Add a user-defined pattern to the cygpath arguments
143 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then
144 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
145 | fi
146 | # Now convert the arguments - kludge to limit ourselves to /bin/sh
147 | i=0
148 | for arg in "$@" ; do
149 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
150 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
151 |
152 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
153 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
154 | else
155 | eval `echo args$i`="\"$arg\""
156 | fi
157 | i=`expr $i + 1`
158 | done
159 | case $i in
160 | 0) set -- ;;
161 | 1) set -- "$args0" ;;
162 | 2) set -- "$args0" "$args1" ;;
163 | 3) set -- "$args0" "$args1" "$args2" ;;
164 | 4) set -- "$args0" "$args1" "$args2" "$args3" ;;
165 | 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
166 | 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
167 | 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
168 | 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
169 | 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
170 | esac
171 | fi
172 |
173 | # Escape application args
174 | save () {
175 | for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
176 | echo " "
177 | }
178 | APP_ARGS=`save "$@"`
179 |
180 | # Collect all arguments for the java command, following the shell quoting and substitution rules
181 | eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
182 |
183 | exec "$JAVACMD" "$@"
184 |
--------------------------------------------------------------------------------
/gradlew.bat:
--------------------------------------------------------------------------------
1 | @rem
2 | @rem Copyright 2015 the original author or authors.
3 | @rem
4 | @rem Licensed under the Apache License, Version 2.0 (the "License");
5 | @rem you may not use this file except in compliance with the License.
6 | @rem You may obtain a copy of the License at
7 | @rem
8 | @rem https://www.apache.org/licenses/LICENSE-2.0
9 | @rem
10 | @rem Unless required by applicable law or agreed to in writing, software
11 | @rem distributed under the License is distributed on an "AS IS" BASIS,
12 | @rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | @rem See the License for the specific language governing permissions and
14 | @rem limitations under the License.
15 | @rem
16 |
17 | @if "%DEBUG%" == "" @echo off
18 | @rem ##########################################################################
19 | @rem
20 | @rem Gradle startup script for Windows
21 | @rem
22 | @rem ##########################################################################
23 |
24 | @rem Set local scope for the variables with windows NT shell
25 | if "%OS%"=="Windows_NT" setlocal
26 |
27 | set DIRNAME=%~dp0
28 | if "%DIRNAME%" == "" set DIRNAME=.
29 | set APP_BASE_NAME=%~n0
30 | set APP_HOME=%DIRNAME%
31 |
32 | @rem Resolve any "." and ".." in APP_HOME to make it shorter.
33 | for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
34 |
35 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
36 | set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
37 |
38 | @rem Find java.exe
39 | if defined JAVA_HOME goto findJavaFromJavaHome
40 |
41 | set JAVA_EXE=java.exe
42 | %JAVA_EXE% -version >NUL 2>&1
43 | if "%ERRORLEVEL%" == "0" goto init
44 |
45 | echo.
46 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
47 | echo.
48 | echo Please set the JAVA_HOME variable in your environment to match the
49 | echo location of your Java installation.
50 |
51 | goto fail
52 |
53 | :findJavaFromJavaHome
54 | set JAVA_HOME=%JAVA_HOME:"=%
55 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe
56 |
57 | if exist "%JAVA_EXE%" goto init
58 |
59 | echo.
60 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
61 | echo.
62 | echo Please set the JAVA_HOME variable in your environment to match the
63 | echo location of your Java installation.
64 |
65 | goto fail
66 |
67 | :init
68 | @rem Get command-line arguments, handling Windows variants
69 |
70 | if not "%OS%" == "Windows_NT" goto win9xME_args
71 |
72 | :win9xME_args
73 | @rem Slurp the command line arguments.
74 | set CMD_LINE_ARGS=
75 | set _SKIP=2
76 |
77 | :win9xME_args_slurp
78 | if "x%~1" == "x" goto execute
79 |
80 | set CMD_LINE_ARGS=%*
81 |
82 | :execute
83 | @rem Setup the command line
84 |
85 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
86 |
87 | @rem Execute Gradle
88 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
89 |
90 | :end
91 | @rem End local scope for the variables with windows NT shell
92 | if "%ERRORLEVEL%"=="0" goto mainEnd
93 |
94 | :fail
95 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
96 | rem the _cmd.exe /c_ return code!
97 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
98 | exit /b 1
99 |
100 | :mainEnd
101 | if "%OS%"=="Windows_NT" endlocal
102 |
103 | :omega
104 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/HeadersMultiMap.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import java.util.List;
29 |
30 | public class HeadersMultiMap extends HttpMultiMap {
31 |
32 | protected HeadersMultiMap() {
33 | super(false);
34 | }
35 |
36 | /**
37 | * Adds new header value. Allows multiple values for the same name.
38 | */
39 | public void addHeader(final String name, final String value) {
40 | List valuesList = super.getAll(name);
41 | if (valuesList.isEmpty()) {
42 | super.add(name, value);
43 | return;
44 | }
45 | super.remove(name);
46 | valuesList.add(value);
47 | super.addAll(name, valuesList);
48 | }
49 |
50 | /**
51 | * Sets the header value. Existing value will bee replaces.
52 | */
53 | public void setHeader(final String name, final String value) {
54 | super.set(name, value);
55 | }
56 |
57 | /**
58 | * Returns header value. In case of multiple values, returns only the first value.
59 | */
60 | public String getHeader(final String name) {
61 | return super.get(name);
62 | }
63 | }
64 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/HttpConnection.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import java.io.IOException;
29 | import java.io.InputStream;
30 | import java.io.OutputStream;
31 |
32 | /**
33 | * Http connection. Created by {@link HttpConnectionProvider}.
34 | */
35 | public interface HttpConnection {
36 |
37 | /**
38 | * Initializes http connection after socket is created.
39 | * Applies configurations, like {@link #setTimeout(int)}.
40 | */
41 | public void init() throws IOException;
42 |
43 | /**
44 | * Returns connection output stream.
45 | */
46 | public OutputStream getOutputStream() throws IOException;
47 |
48 | /**
49 | * Returns connection input stream.
50 | */
51 | public InputStream getInputStream() throws IOException;
52 |
53 | /**
54 | * Closes connection. Ignores all exceptions.
55 | */
56 | public void close();
57 |
58 | /**
59 | * Sets the timeout for connections, in milliseconds. With this option set to a non-zero timeout,
60 | * connection will block for only this amount of time. If the timeout expires, an Exception is raised.
61 | * The timeout must be > 0. A timeout of zero is interpreted as an infinite timeout.
62 | */
63 | void setTimeout(int milliseconds);
64 |
65 | }
--------------------------------------------------------------------------------
/src/main/java/jodd/http/HttpConnectionProvider.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.http.net.SocketHttpConnectionProvider;
29 |
30 | import java.io.IOException;
31 |
32 | /**
33 | * Factory for {@link HttpConnection http connections}.
34 | */
35 | public interface HttpConnectionProvider {
36 |
37 | class Implementation {
38 | private static HttpConnectionProvider httpConnectionProvider = new SocketHttpConnectionProvider();
39 |
40 | public static void set(final HttpConnectionProvider httpConnectionProvider) {
41 | Implementation.httpConnectionProvider = httpConnectionProvider;
42 | }
43 | }
44 |
45 | /**
46 | * Returns default implementation of connection provider.
47 | */
48 | static HttpConnectionProvider get() {
49 | return Implementation.httpConnectionProvider;
50 | }
51 |
52 |
53 | /**
54 | * Specifies {@link ProxyInfo proxy} for provide to use.
55 | */
56 | public void useProxy(ProxyInfo proxyInfo);
57 |
58 | /**
59 | * Creates new {@link HttpConnection}
60 | * from {@link jodd.http.HttpRequest request}.
61 | */
62 | public HttpConnection createHttpConnection(HttpRequest httpRequest) throws IOException;
63 |
64 | }
--------------------------------------------------------------------------------
/src/main/java/jodd/http/HttpException.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.exception.UncheckedException;
29 |
30 | /**
31 | * HTTP exception.
32 | */
33 | public class HttpException extends UncheckedException {
34 |
35 | public HttpException(final Throwable t) {
36 | super(t);
37 | }
38 |
39 | public HttpException(final String message) {
40 | super(message);
41 | }
42 |
43 | public HttpException(final Object networkObject, final String message) {
44 | super(networkObject.toString() + ": " + message);
45 | }
46 |
47 | public HttpException(final String message, final Throwable t) {
48 | super(message, t);
49 | }
50 |
51 | public HttpException(final Object networkObject, final String message, final Throwable t) {
52 | super(networkObject.toString() + ": " + message, t);
53 | }
54 | }
55 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/HttpProgressListener.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | /**
29 | * Http upload progress listener.
30 | */
31 | public abstract class HttpProgressListener {
32 |
33 | /**
34 | * Total size to transfer.
35 | */
36 | protected int size;
37 |
38 | /**
39 | * Returns callback size in bytes. By default it returns
40 | * size of 1 percent of a total size. If returned size
41 | * is less then 512, it will be rounded to 512.
42 | * This is also the size of the chunk that is sent over network.
43 | */
44 | public int callbackSize(final int size) {
45 | this.size = size;
46 |
47 | int callbackSize = (size + 50) / 100;
48 |
49 | if (callbackSize < 512) {
50 | callbackSize = 512;
51 | }
52 |
53 | return callbackSize;
54 | }
55 |
56 | /**
57 | * Callback for every sent {@link #callbackSize(int) chunk}.
58 | * Also called before and after the transfer.
59 | */
60 | public abstract void transferred(int len);
61 |
62 | }
--------------------------------------------------------------------------------
/src/main/java/jodd/http/HttpTunnel.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.io.IOUtil;
29 |
30 | import java.io.IOException;
31 | import java.io.InputStream;
32 | import java.io.OutputStream;
33 | import java.net.ServerSocket;
34 | import java.net.Socket;
35 | import java.util.concurrent.ExecutorService;
36 | import java.util.concurrent.Executors;
37 |
38 | /**
39 | * Simple HTTP tunnel base ready to be extended.
40 | */
41 | public class HttpTunnel {
42 |
43 | /**
44 | * The number of threads that can be executed in parallel.
45 | */
46 | protected int threadPoolSize = 10;
47 |
48 | /**
49 | * Number of incoming sockets connection that can be hold
50 | * before processing each.
51 | */
52 | protected int socketBacklog = 100;
53 |
54 | /**
55 | * Tunnel listening port.
56 | */
57 | protected int listenPort = 8888;
58 |
59 | /**
60 | * Target host.
61 | */
62 | protected String targetHost = "localhost";
63 |
64 | /**
65 | * Target port.
66 | */
67 | protected int targetPort = 8080;
68 |
69 | protected ExecutorService executorService;
70 | protected volatile boolean running;
71 | protected ServerSocket serverSocket;
72 |
73 | /**
74 | * Starts HTTP tunnel. Method ends when the tunnel is stopped.
75 | */
76 | public void start() throws IOException {
77 | serverSocket = new ServerSocket(listenPort, socketBacklog);
78 | serverSocket.setReuseAddress(true);
79 | executorService = Executors.newFixedThreadPool(threadPoolSize);
80 |
81 | running = true;
82 | while (running) {
83 | final Socket socket = serverSocket.accept();
84 | socket.setKeepAlive(false);
85 | executorService.execute(onSocketConnection(socket));
86 | }
87 | executorService.shutdown();
88 | }
89 |
90 | /**
91 | * Invoked on incoming connection. By default returns {@link HttpTunnelConnection}
92 | * to handle the connection. May be used to return custom
93 | * handlers.
94 | */
95 | protected Runnable onSocketConnection(final Socket socket) {
96 | return new HttpTunnelConnection(socket);
97 | }
98 |
99 | /**
100 | * Stops the tunnel, shutdowns the thread pool and closes server socket.
101 | */
102 | public void stop() {
103 | running = false;
104 | executorService.shutdown();
105 | try {
106 | serverSocket.close();
107 | } catch (final IOException ignore) {
108 | }
109 | }
110 |
111 | /**
112 | * Single connection handler that performs the tunneling.
113 | */
114 | public class HttpTunnelConnection implements Runnable {
115 |
116 | protected final Socket socket;
117 |
118 | public HttpTunnelConnection(final Socket socket) {
119 | this.socket = socket;
120 | }
121 |
122 | @Override
123 | public void run() {
124 | try {
125 | tunnel();
126 | } catch (final IOException ioex) {
127 | ioex.printStackTrace();
128 | }
129 | }
130 |
131 | /**
132 | * Invoked after income connection is parsed. Nothing is
133 | * changed in the request, except the target host and port.
134 | */
135 | protected void onRequest(final HttpRequest request) {
136 | }
137 |
138 | /**
139 | * Invoked after target response is processed. Response is now
140 | * ready to be sent back to the client. The following header
141 | * parameters are changed:
142 | *
143 | * - Transfer-Encoding is removed, as body is returned at once,
144 | * - Content-Length is added/update to body size.
145 | *
146 | */
147 | protected void onResponse(final HttpResponse response) {
148 | }
149 |
150 | /**
151 | * Performs the tunneling. The following steps occurs:
152 | *
153 | * - read and parse clients request
154 | * - open socket to target
155 | * - resend request to target
156 | * - read targets response
157 | * - fix response and resend it to client
158 | *
159 | */
160 | protected void tunnel() throws IOException {
161 |
162 | // read request
163 | final InputStream socketInput = socket.getInputStream();
164 | final HttpRequest request = HttpRequest.readFrom(socketInput);
165 |
166 | // open client socket to target
167 | final Socket clientSocket = Sockets.connect(targetHost, targetPort);
168 |
169 | // do request
170 | request.host(targetHost);
171 | request.port(targetPort);
172 | request.setHostHeader();
173 | onRequest(request);
174 |
175 | // resend request to target
176 | final OutputStream out = clientSocket.getOutputStream();
177 | request.sendTo(out);
178 |
179 | // read target response
180 | final InputStream in = clientSocket.getInputStream();
181 | final HttpResponse response = HttpResponse.readFrom(in);
182 |
183 | // close client socket
184 | IOUtil.close(in);
185 | IOUtil.close(out);
186 | try {
187 | clientSocket.close();
188 | } catch (final IOException ignore) {
189 | }
190 |
191 | // fix response
192 | if (response.bodyRaw() != null) {
193 | response.headerRemove("Transfer-Encoding");
194 | response.contentLength(response.bodyRaw().length());
195 | }
196 |
197 | // do response
198 | onResponse(response);
199 |
200 | // send response back
201 | final OutputStream socketOutput = socket.getOutputStream();
202 | response.sendTo(socketOutput);
203 |
204 | // close socket
205 | IOUtil.close(socketInput);
206 | IOUtil.close(socketOutput);
207 | try {
208 | socket.close();
209 | } catch (final IOException ignore) {
210 | }
211 | }
212 | }
213 |
214 | }
215 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/ProxyInfo.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | /**
29 | * Proxy information.
30 | */
31 | public class ProxyInfo {
32 |
33 | /**
34 | * Proxy types.
35 | */
36 | public enum ProxyType {
37 | NONE, HTTP, SOCKS4, SOCKS5
38 | }
39 |
40 | private final String proxyAddress;
41 | private final int proxyPort;
42 | private final String proxyUsername;
43 | private final String proxyPassword;
44 | private final ProxyType proxyType;
45 |
46 | public ProxyInfo(final ProxyType proxyType, final String proxyHost, final int proxyPort, final String proxyUser, final String proxyPassword) {
47 | this.proxyType = proxyType;
48 | this.proxyAddress = proxyHost;
49 | this.proxyPort = proxyPort;
50 | this.proxyUsername = proxyUser;
51 | this.proxyPassword = proxyPassword;
52 | }
53 |
54 | // ---------------------------------------------------------------- factory
55 |
56 | /**
57 | * Creates directProxy.
58 | */
59 | public static ProxyInfo directProxy() {
60 | return new ProxyInfo(ProxyType.NONE, null, 0, null, null);
61 | }
62 |
63 | /**
64 | * Creates SOCKS4 proxy.
65 | */
66 | public static ProxyInfo socks4Proxy(final String proxyAddress, final int proxyPort, final String proxyUser) {
67 | return new ProxyInfo(ProxyType.SOCKS4, proxyAddress, proxyPort, proxyUser, null);
68 | }
69 |
70 | /**
71 | * Creates SOCKS5 proxy.
72 | */
73 | public static ProxyInfo socks5Proxy(final String proxyAddress, final int proxyPort, final String proxyUser, final String proxyPassword) {
74 | return new ProxyInfo(ProxyType.SOCKS5, proxyAddress, proxyPort, proxyUser, proxyPassword);
75 | }
76 |
77 | /**
78 | * Creates HTTP proxy.
79 | */
80 | public static ProxyInfo httpProxy(final String proxyAddress, final int proxyPort, final String proxyUser, final String proxyPassword) {
81 | return new ProxyInfo(ProxyType.HTTP, proxyAddress, proxyPort, proxyUser, proxyPassword);
82 | }
83 |
84 | // ---------------------------------------------------------------- getter
85 |
86 | /**
87 | * Returns proxy type.
88 | */
89 | public ProxyType getProxyType() {
90 | return proxyType;
91 | }
92 |
93 | /**
94 | * Returns proxy address.
95 | */
96 | public String getProxyAddress() {
97 | return proxyAddress;
98 | }
99 |
100 | /**
101 | * Returns proxy port.
102 | */
103 | public int getProxyPort() {
104 | return proxyPort;
105 | }
106 |
107 | /**
108 | * Returns proxy user name or null
if
109 | * no authentication required.
110 | */
111 | public String getProxyUsername() {
112 | return proxyUsername;
113 | }
114 |
115 | /**
116 | * Returns proxy password or null
.
117 | */
118 | public String getProxyPassword() {
119 | return proxyPassword;
120 | }
121 |
122 | }
--------------------------------------------------------------------------------
/src/main/java/jodd/http/Sockets.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import java.io.IOException;
29 | import java.net.InetSocketAddress;
30 | import java.net.Socket;
31 |
32 | /**
33 | * Sockets factory.
34 | */
35 | public class Sockets {
36 |
37 | /**
38 | * Creates a socket.
39 | */
40 | public static Socket connect(final String hostname, final int port) throws IOException {
41 | final Socket socket = new Socket();
42 | socket.connect(new InetSocketAddress(hostname, port));
43 | return socket;
44 | }
45 |
46 | /**
47 | * Creates a socket with a timeout.
48 | */
49 | public static Socket connect(final String hostname, final int port, final int connectionTimeout) throws IOException {
50 | final Socket socket = new Socket();
51 | if (connectionTimeout <= 0) {
52 | socket.connect(new InetSocketAddress(hostname, port));
53 | }
54 | else {
55 | socket.connect(new InetSocketAddress(hostname, port), connectionTimeout);
56 | }
57 | return socket;
58 | }
59 | }
60 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/net/HTTPProxySocketFactory.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.net;
27 |
28 | import jodd.http.HttpException;
29 | import jodd.http.ProxyInfo;
30 | import jodd.http.Sockets;
31 | import jodd.util.Base64;
32 |
33 | import javax.net.SocketFactory;
34 | import java.io.BufferedReader;
35 | import java.io.InputStream;
36 | import java.io.StringReader;
37 | import java.net.HttpURLConnection;
38 | import java.net.InetAddress;
39 | import java.net.Socket;
40 | import java.nio.charset.StandardCharsets;
41 | import java.util.regex.Matcher;
42 | import java.util.regex.Pattern;
43 |
44 | /**
45 | * Socket factory for HTTP proxy.
46 | */
47 | public class HTTPProxySocketFactory extends SocketFactory {
48 |
49 | private final ProxyInfo proxy;
50 | private final int connectionTimeout;
51 |
52 | public HTTPProxySocketFactory(final ProxyInfo proxy, final int connectionTimeout) {
53 | this.proxy = proxy;
54 | this.connectionTimeout = connectionTimeout;
55 | }
56 |
57 | @Override
58 | public Socket createSocket() {
59 | return new Socket();
60 | }
61 |
62 | @Override
63 | public Socket createSocket(final String host, final int port) {
64 | return createHttpProxySocket(host, port);
65 | }
66 |
67 | @Override
68 | public Socket createSocket(final String host, final int port, final InetAddress localHost, final int localPort) {
69 | return createHttpProxySocket(host, port);
70 | }
71 |
72 | @Override
73 | public Socket createSocket(final InetAddress host, final int port) {
74 | return createHttpProxySocket(host.getHostAddress(), port);
75 | }
76 |
77 | @Override
78 | public Socket createSocket(final InetAddress address, final int port, final InetAddress localAddress, final int localPort) {
79 | return createHttpProxySocket(address.getHostAddress(), port);
80 | }
81 |
82 | private Socket createHttpProxySocket(final String host, final int port) {
83 | Socket socket = null;
84 | final String proxyAddress = proxy.getProxyAddress();
85 | final int proxyPort = proxy.getProxyPort();
86 |
87 | try {
88 | socket = Sockets.connect(proxyAddress, proxyPort, connectionTimeout);
89 | final String hostport = host + ":" + port;
90 | String proxyLine = "";
91 | final String username = proxy.getProxyUsername();
92 |
93 | if (username != null) {
94 | final String password = proxy.getProxyPassword();
95 | proxyLine =
96 | "Proxy-Authorization: Basic " +
97 | Base64.encodeToString((username + ":" + password)) + "\r\n";
98 | }
99 |
100 | socket.getOutputStream().write(
101 | ("CONNECT " + hostport + " HTTP/1.1\r\n" +
102 | "Host: " + hostport + "\r\n" +
103 | proxyLine +
104 | "\r\n"
105 | ).getBytes(StandardCharsets.UTF_8)
106 | );
107 |
108 | final InputStream in = socket.getInputStream();
109 | final StringBuilder recv = new StringBuilder(100);
110 | int nlchars = 0;
111 |
112 | do {
113 | final int i = in.read();
114 | if (i == -1) {
115 | throw new HttpException(ProxyInfo.ProxyType.HTTP, "Invalid response");
116 | }
117 |
118 | final char c = (char) i;
119 | recv.append(c);
120 | if (recv.length() > 1024) {
121 | throw new HttpException(ProxyInfo.ProxyType.HTTP, "Received header longer then 1024 chars");
122 | }
123 | if ((nlchars == 0 || nlchars == 2) && c == '\r') {
124 | nlchars++;
125 | } else if ((nlchars == 1 || nlchars == 3) && c == '\n') {
126 | nlchars++;
127 | } else {
128 | nlchars = 0;
129 | }
130 | } while (nlchars != 4);
131 |
132 | final String recvStr = recv.toString();
133 |
134 | final BufferedReader br = new BufferedReader(new StringReader(recvStr));
135 | final String response = br.readLine();
136 |
137 | if (response == null) {
138 | throw new HttpException(ProxyInfo.ProxyType.HTTP, "Empty proxy response");
139 | }
140 |
141 | final Matcher m = RESPONSE_PATTERN.matcher(response);
142 | if (!m.matches()) {
143 | throw new HttpException(ProxyInfo.ProxyType.HTTP, "Unexpected proxy response");
144 | }
145 |
146 | final int code = Integer.parseInt(m.group(1));
147 |
148 | if (code != HttpURLConnection.HTTP_OK) {
149 | throw new HttpException(ProxyInfo.ProxyType.HTTP, "Invalid return status code: " + code);
150 | }
151 |
152 | return socket;
153 | } catch (final RuntimeException rtex) {
154 | closeSocket(socket);
155 | throw rtex;
156 | } catch (final Exception ex) {
157 | closeSocket(socket);
158 | throw new HttpException(ProxyInfo.ProxyType.HTTP, ex.toString(), ex);
159 | }
160 |
161 | }
162 |
163 | /**
164 | * Closes socket silently.
165 | */
166 | private void closeSocket(final Socket socket) {
167 | try {
168 | if (socket != null) {
169 | socket.close();
170 | }
171 | } catch (final Exception ignore) {
172 | }
173 | }
174 |
175 | private static final Pattern RESPONSE_PATTERN =
176 | Pattern.compile("HTTP/\\S+\\s(\\d+)\\s(.*)\\s*");
177 | }
178 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/net/SSLSocketHttpConnectionProvider.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.net;
27 |
28 | import jodd.http.ProxyInfo;
29 |
30 | import javax.net.SocketFactory;
31 | import javax.net.ssl.SSLContext;
32 | import javax.net.ssl.SSLSocketFactory;
33 |
34 | /**
35 | * Custom SSL socket http connection provider.
36 | */
37 | public class SSLSocketHttpConnectionProvider extends SocketHttpConnectionProvider {
38 |
39 | private final SSLSocketFactory socketFactory;
40 |
41 | public SSLSocketHttpConnectionProvider(final SSLSocketFactory sslSocketFactory) {
42 | this.socketFactory = sslSocketFactory;
43 | }
44 |
45 | public SSLSocketHttpConnectionProvider(final SSLContext sslContext) {
46 | this.socketFactory = sslContext.getSocketFactory();
47 | }
48 |
49 | @Override
50 | protected SocketFactory resolveSocketFactory(
51 | final ProxyInfo proxy,
52 | final boolean ssl,
53 | final boolean trustAllCertificates,
54 | final int connectionTimeout) {
55 | return socketFactory;
56 | }
57 | }
58 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/net/SocketHttpConnection.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.net;
27 |
28 | import jodd.http.HttpConnection;
29 |
30 | import java.io.IOException;
31 | import java.io.InputStream;
32 | import java.io.OutputStream;
33 | import java.net.Socket;
34 |
35 | /**
36 | * Socket-based {@link jodd.http.HttpConnection}.
37 | * @see SocketHttpConnectionProvider
38 | */
39 | public class SocketHttpConnection implements HttpConnection {
40 |
41 | protected final Socket socket;
42 |
43 | public SocketHttpConnection(final Socket socket) {
44 | this.socket = socket;
45 | }
46 |
47 | @Override
48 | public void init() throws IOException {
49 | if (timeout >= 0) {
50 | socket.setSoTimeout(timeout);
51 | }
52 | }
53 |
54 | @Override
55 | public OutputStream getOutputStream() throws IOException {
56 | return socket.getOutputStream();
57 | }
58 |
59 | @Override
60 | public InputStream getInputStream() throws IOException {
61 | return socket.getInputStream();
62 | }
63 |
64 | @Override
65 | public void close() {
66 | try {
67 | socket.close();
68 | } catch (Throwable ignore) {
69 | }
70 | }
71 |
72 | @Override
73 | public void setTimeout(final int milliseconds) {
74 | this.timeout = milliseconds;
75 | }
76 |
77 | /**
78 | * Returns Socket
used by this connection.
79 | */
80 | public Socket getSocket() {
81 | return socket;
82 | }
83 |
84 | private int timeout;
85 | }
--------------------------------------------------------------------------------
/src/main/java/jodd/http/net/SocketHttpSecureConnection.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.net;
27 |
28 | import javax.net.ssl.SSLSocket;
29 | import java.io.IOException;
30 |
31 | public class SocketHttpSecureConnection extends SocketHttpConnection {
32 | private final SSLSocket sslSocket;
33 |
34 | public SocketHttpSecureConnection(final SSLSocket socket) {
35 | super(socket);
36 | this.sslSocket = socket;
37 | }
38 |
39 | @Override
40 | public void init() throws IOException {
41 | super.init();
42 |
43 | sslSocket.startHandshake();
44 | }
45 | }
--------------------------------------------------------------------------------
/src/main/java/jodd/http/net/Socks4ProxySocketFactory.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.net;
27 |
28 | import jodd.http.HttpException;
29 | import jodd.http.ProxyInfo;
30 | import jodd.http.Sockets;
31 |
32 | import javax.net.SocketFactory;
33 | import java.io.InputStream;
34 | import java.io.OutputStream;
35 | import java.net.InetAddress;
36 | import java.net.Socket;
37 |
38 | /**
39 | * Socket factory for SOCKS4 proxy. This proxy does not do password authentication.
40 | *
41 | * See: http://www.openssh.com/txt/socks5.protocol for more details.
42 | */
43 | public class Socks4ProxySocketFactory extends SocketFactory {
44 |
45 | private final ProxyInfo proxy;
46 | private final int connectionTimeout;
47 |
48 | public Socks4ProxySocketFactory(final ProxyInfo proxy, final int connectionTimeout) {
49 | this.proxy = proxy;
50 | this.connectionTimeout = connectionTimeout;
51 | }
52 |
53 | @Override
54 | public Socket createSocket() {
55 | return new Socket();
56 | }
57 |
58 | @Override
59 | public Socket createSocket(final String host, final int port) {
60 | return createSocks4ProxySocket(host, port);
61 | }
62 |
63 | @Override
64 | public Socket createSocket(final String host, final int port, final InetAddress localHost, final int localPort) {
65 | return createSocks4ProxySocket(host, port);
66 | }
67 |
68 | @Override
69 | public Socket createSocket(final InetAddress host, final int port) {
70 | return createSocks4ProxySocket(host.getHostAddress(), port);
71 | }
72 |
73 | @Override
74 | public Socket createSocket(final InetAddress address, final int port, final InetAddress localAddress, final int localPort) {
75 | return createSocks4ProxySocket(address.getHostAddress(), port);
76 | }
77 |
78 | /**
79 | * Connects to the SOCKS4 proxy and returns proxified socket.
80 | */
81 | private Socket createSocks4ProxySocket(final String host, final int port) {
82 | Socket socket = null;
83 | final String proxyHost = proxy.getProxyAddress();
84 | final int proxyPort = proxy.getProxyPort();
85 | final String user = proxy.getProxyUsername();
86 |
87 | try {
88 | socket = Sockets.connect(proxyHost, proxyPort, connectionTimeout);
89 |
90 | final InputStream in = socket.getInputStream();
91 | final OutputStream out = socket.getOutputStream();
92 |
93 | socket.setTcpNoDelay(true);
94 |
95 | final byte[] buf = new byte[1024];
96 |
97 | // 1) CONNECT
98 |
99 | int index = 0;
100 | buf[index++] = 4;
101 | buf[index++] = 1;
102 |
103 | buf[index++] = (byte) (port >>> 8);
104 | buf[index++] = (byte) (port & 0xff);
105 |
106 | final InetAddress addr = InetAddress.getByName(host);
107 | final byte[] byteAddress = addr.getAddress();
108 | for (final byte byteAddres : byteAddress) {
109 | buf[index++] = byteAddres;
110 | }
111 |
112 | if (user != null) {
113 | System.arraycopy(user.getBytes(), 0, buf, index, user.length());
114 | index += user.length();
115 | }
116 | buf[index++] = 0;
117 | out.write(buf, 0, index);
118 |
119 | // 2) RESPONSE
120 |
121 | final int len = 6;
122 | int s = 0;
123 | while (s < len) {
124 | final int i = in.read(buf, s, len - s);
125 | if (i <= 0) {
126 | throw new HttpException(ProxyInfo.ProxyType.SOCKS4, "stream is closed");
127 | }
128 | s += i;
129 | }
130 | if (buf[0] != 0) {
131 | throw new HttpException(ProxyInfo.ProxyType.SOCKS4, "proxy returned VN " + buf[0]);
132 | }
133 | if (buf[1] != 90) {
134 | try {
135 | socket.close();
136 | } catch (final Exception ignore) {
137 | }
138 | throw new HttpException(ProxyInfo.ProxyType.SOCKS4, "proxy returned CD " + buf[1]);
139 | }
140 |
141 | final byte[] temp = new byte[2];
142 | in.read(temp, 0, 2);
143 |
144 | return socket;
145 | } catch (final RuntimeException rtex) {
146 | closeSocket(socket);
147 | throw rtex;
148 | } catch (final Exception ex) {
149 | closeSocket(socket);
150 | throw new HttpException(ProxyInfo.ProxyType.SOCKS4, ex.toString(), ex);
151 | }
152 | }
153 |
154 | /**
155 | * Closes socket silently.
156 | */
157 | private void closeSocket(final Socket socket) {
158 | try {
159 | if (socket != null) {
160 | socket.close();
161 | }
162 | } catch (final Exception ignore) {
163 | }
164 | }
165 | }
166 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/net/TrustManagers.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 | package jodd.http.net;
26 |
27 | import javax.net.ssl.SSLEngine;
28 | import javax.net.ssl.TrustManager;
29 | import javax.net.ssl.X509ExtendedTrustManager;
30 | import java.net.Socket;
31 | import java.security.cert.X509Certificate;
32 |
33 | public class TrustManagers {
34 | /**
35 | * Array of trust managers that allow all certificates, done in Java8 proper-way.
36 | */
37 | public static TrustManager[] TRUST_ALL_CERTS = new TrustManager[]{
38 | new X509ExtendedTrustManager() {
39 | @Override
40 | public void checkClientTrusted(final X509Certificate[] x509Certificates, final String s) {
41 | }
42 | @Override
43 | public void checkServerTrusted(final X509Certificate[] x509Certificates, final String s) {
44 | }
45 | @Override
46 | public X509Certificate[] getAcceptedIssuers() {
47 | return null;
48 | }
49 | @Override
50 | public void checkClientTrusted(final X509Certificate[] x509Certificates, final String s, final Socket socket) {
51 | }
52 | @Override
53 | public void checkServerTrusted(final X509Certificate[] x509Certificates, final String s, final Socket socket) {
54 | }
55 | @Override
56 | public void checkClientTrusted(final X509Certificate[] x509Certificates, final String s, final SSLEngine sslEngine) {
57 | }
58 | @Override
59 | public void checkServerTrusted(final X509Certificate[] x509Certificates, final String s, final SSLEngine sslEngine) {
60 | }
61 | }
62 | };
63 | }
64 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/net/package-info.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | /**
27 | * Implementations and core HTTP stuff.
28 | */
29 | package jodd.http.net;
--------------------------------------------------------------------------------
/src/main/java/jodd/http/package-info.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | /**
27 | * Tiny, raw and simple socket-based HTTP client.
28 | */
29 | package jodd.http;
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/ByteArrayUploadable.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload;
27 |
28 | import java.io.ByteArrayInputStream;
29 | import java.io.InputStream;
30 |
31 | /**
32 | * Uploadable wrapper of byte array
.
33 | */
34 | public class ByteArrayUploadable implements Uploadable {
35 |
36 | protected final byte[] byteArray;
37 | protected final String fileName;
38 | protected final String mimeType;
39 |
40 | public ByteArrayUploadable(final byte[] byteArray, final String fileName) {
41 | this.byteArray = byteArray;
42 | this.fileName = fileName;
43 | this.mimeType = null;
44 | }
45 |
46 | public ByteArrayUploadable(final byte[] byteArray, final String fileName, final String mimeType) {
47 | this.byteArray = byteArray;
48 | this.fileName = fileName;
49 | this.mimeType = mimeType;
50 | }
51 |
52 | @Override
53 | public byte[] getContent() {
54 | return byteArray;
55 | }
56 |
57 | @Override
58 | public byte[] getBytes() {
59 | return byteArray;
60 | }
61 |
62 | @Override
63 | public String getFileName() {
64 | return fileName;
65 | }
66 |
67 | @Override
68 | public String getMimeType() {
69 | return mimeType;
70 | }
71 |
72 | @Override
73 | public int getSize() {
74 | return byteArray.length;
75 | }
76 |
77 | @Override
78 | public InputStream openInputStream() {
79 | return new ByteArrayInputStream(byteArray);
80 | }
81 | }
82 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/FileUpload.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload;
27 |
28 | import java.io.IOException;
29 | import java.io.InputStream;
30 |
31 | /**
32 | * Encapsulates base for uploaded file. Its instance may be
33 | * either valid, when it represent an uploaded file, or invalid
34 | * when uploaded file doesn't exist or there was a problem with it.
35 | */
36 | public abstract class FileUpload {
37 |
38 | protected final MultipartRequestInputStream input;
39 | protected final int maxFileSize;
40 | protected final FileUploadHeader header;
41 |
42 | protected FileUpload(final MultipartRequestInputStream input, final int maxFileSize) {
43 | this.input = input;
44 | this.header = input.lastHeader;
45 | this.maxFileSize = maxFileSize;
46 | }
47 |
48 | // ---------------------------------------------------------------- header
49 |
50 | /**
51 | * Returns {@link FileUploadHeader} of uploaded file.
52 | */
53 | public FileUploadHeader getHeader() {
54 | return header;
55 | }
56 |
57 | // ---------------------------------------------------------------- data
58 |
59 | /**
60 | * Returns all bytes of uploaded file.
61 | */
62 | public abstract byte[] getFileContent() throws IOException;
63 |
64 | /**
65 | * Returns input stream of uploaded file.
66 | */
67 | public abstract InputStream getFileInputStream() throws IOException;
68 |
69 | // ---------------------------------------------------------------- size and validity
70 |
71 | protected boolean valid;
72 |
73 | protected int size = -1;
74 |
75 | protected boolean fileTooBig;
76 |
77 | /**
78 | * Returns the file upload size or -1
if file was not uploaded.
79 | */
80 | public int getSize() {
81 | return size;
82 | }
83 |
84 | /**
85 | * Returns true
if file was uploaded.
86 | */
87 | public boolean isUploaded() {
88 | return size != -1;
89 | }
90 |
91 | /**
92 | * Returns true
if upload process went correctly.
93 | * This still does not mean that file is uploaded, e.g. when file
94 | * was not specified on the form.
95 | */
96 | public boolean isValid() {
97 | return valid;
98 | }
99 |
100 | /**
101 | * Returns max file size or -1
if there is no max file size.
102 | */
103 | public int getMaxFileSize() {
104 | return maxFileSize;
105 | }
106 |
107 | /**
108 | * Returns true
if file is too big. File will be marked as invalid.
109 | */
110 | public boolean isFileTooBig() {
111 | return fileTooBig;
112 | }
113 |
114 | // ---------------------------------------------------------------- status
115 |
116 | /**
117 | * Returns true
if uploaded file content is stored in memory.
118 | */
119 | public abstract boolean isInMemory();
120 |
121 | // ---------------------------------------------------------------- process
122 |
123 | /**
124 | * Process request input stream. Note that file size is unknown at this point.
125 | * Therefore, the implementation should set the {@link #getSize() size}
126 | * attribute after successful processing. This method also must set the
127 | * {@link #isValid() valid} attribute.
128 | *
129 | * @see MultipartRequestInputStream
130 | */
131 | protected abstract void processStream() throws IOException;
132 |
133 | // ---------------------------------------------------------------- toString
134 |
135 | /**
136 | * Returns basic information about the uploaded file.
137 | */
138 | @Override
139 | public String toString() {
140 | return "FileUpload: uploaded=[" + isUploaded() + "] valid=[" + valid + "] field=[" +
141 | header.getFormFieldName() + "] name=[" + header.getFileName() + "] size=[" + size + ']';
142 | }
143 | }
144 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/FileUploadFactory.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload;
27 |
28 | /**
29 | * {@link FileUpload} factory for handling uploaded files. Implementations may
30 | * handle uploaded files differently: to store them to memory, directly to disk
31 | * or something else.
32 | */
33 | @FunctionalInterface
34 | public interface FileUploadFactory {
35 |
36 | /**
37 | * Creates new instance of {@link FileUpload uploaded file}.
38 | */
39 | FileUpload create(MultipartRequestInputStream input);
40 | }
41 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/FileUploadHeader.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload;
27 |
28 | import jodd.io.FileNameUtil;
29 | import jodd.util.StringPool;
30 |
31 | /**
32 | * Parses file upload header.
33 | */
34 | public class FileUploadHeader {
35 |
36 | String dataHeader;
37 | String formFieldName;
38 |
39 | String formFileName;
40 | String path;
41 | String fileName;
42 |
43 | boolean isFile;
44 | String contentType;
45 | String mimeType;
46 | String mimeSubtype;
47 | String contentDisposition;
48 |
49 |
50 | FileUploadHeader(final String dataHeader) {
51 | this.dataHeader = dataHeader;
52 | isFile = dataHeader.indexOf("filename") > 0;
53 | formFieldName = getDataFieldValue(dataHeader, "name");
54 | if (isFile) {
55 | formFileName = getDataFieldValue(dataHeader, "filename");
56 | if (formFileName == null) {
57 | return;
58 | }
59 | if (formFileName.length() == 0) {
60 | path = StringPool.EMPTY;
61 | fileName = StringPool.EMPTY;
62 | }
63 | int ls = FileNameUtil.indexOfLastSeparator(formFileName);
64 | if (ls == -1) {
65 | path = StringPool.EMPTY;
66 | fileName = formFileName;
67 | } else {
68 | path = formFileName.substring(0, ls);
69 | fileName = formFileName.substring(ls + 1);
70 | }
71 | if (fileName.length() > 0) {
72 | this.contentType = getContentType(dataHeader);
73 | mimeType = getMimeType(contentType);
74 | mimeSubtype = getMimeSubtype(contentType);
75 | contentDisposition = getContentDisposition(dataHeader);
76 | }
77 | }
78 | }
79 |
80 | // ---------------------------------------------------------------- utilities
81 |
82 | /**
83 | * Gets value of data field or null
if field not found.
84 | */
85 | private String getDataFieldValue(final String dataHeader, final String fieldName) {
86 | String value = null;
87 | String token = String.valueOf((new StringBuffer(String.valueOf(fieldName))).append('=').append('"'));
88 | int pos = dataHeader.indexOf(token);
89 | if (pos > 0) {
90 | int start = pos + token.length();
91 | int end = dataHeader.indexOf('"', start);
92 | if ((start > 0) && (end > 0)) {
93 | value = dataHeader.substring(start, end);
94 | }
95 | }
96 | return value;
97 | }
98 |
99 | /**
100 | * Strips content type information from requests data header.
101 | * @param dataHeader data header string
102 | * @return content type or an empty string if no content type defined
103 | */
104 | private String getContentType(final String dataHeader) {
105 | String token = "Content-Type:";
106 | int start = dataHeader.indexOf(token);
107 | if (start == -1) {
108 | return StringPool.EMPTY;
109 | }
110 | start += token.length();
111 | return dataHeader.substring(start).trim();
112 | }
113 |
114 | private String getContentDisposition(final String dataHeader) {
115 | int start = dataHeader.indexOf(':') + 1;
116 | int end = dataHeader.indexOf(';');
117 | return dataHeader.substring(start, end);
118 | }
119 |
120 | private String getMimeType(final String ContentType) {
121 | int pos = ContentType.indexOf('/');
122 | if (pos == -1) {
123 | return ContentType;
124 | }
125 | return ContentType.substring(1, pos);
126 | }
127 |
128 | private String getMimeSubtype(final String ContentType) {
129 | int start = ContentType.indexOf('/');
130 | if (start == -1) {
131 | return ContentType;
132 | }
133 | start++;
134 | return ContentType.substring(start);
135 | }
136 |
137 |
138 | // ---------------------------------------------------------------- public interface
139 |
140 | /**
141 | * Returns true
if uploaded data are correctly marked as a file.
142 | * This is true if header contains string 'filename'.
143 | */
144 | public boolean isFile() {
145 | return isFile;
146 | }
147 |
148 | /**
149 | * Returns form field name.
150 | */
151 | public String getFormFieldName() {
152 | return formFieldName;
153 | }
154 |
155 | /**
156 | * Returns complete file name as specified at client side.
157 | */
158 | public String getFormFilename() {
159 | return formFileName;
160 | }
161 |
162 | /**
163 | * Returns file name (base name and extension, without full path data).
164 | */
165 | public String getFileName() {
166 | return fileName;
167 | }
168 |
169 | /**
170 | * Returns uploaded content type. It is usually in the following form:
171 | * mime_type/mime_subtype.
172 | *
173 | * @see #getMimeType()
174 | * @see #getMimeSubtype()
175 | */
176 | public String getContentType() {
177 | return contentType;
178 | }
179 |
180 | /**
181 | * Returns file types MIME.
182 | */
183 | public String getMimeType() {
184 | return mimeType;
185 | }
186 |
187 | /**
188 | * Returns file sub type MIME.
189 | */
190 | public String getMimeSubtype() {
191 | return mimeSubtype;
192 | }
193 |
194 | /**
195 | * Returns content disposition. Usually it is 'form-data'.
196 | */
197 | public String getContentDisposition() {
198 | return contentDisposition;
199 | }
200 | }
201 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/FileUploadable.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload;
27 |
28 | import jodd.http.HttpException;
29 | import jodd.io.FileNameUtil;
30 | import jodd.io.FileUtil;
31 |
32 | import java.io.File;
33 | import java.io.FileInputStream;
34 | import java.io.IOException;
35 | import java.io.InputStream;
36 |
37 | /**
38 | * File uploadable.
39 | */
40 | public class FileUploadable implements Uploadable {
41 |
42 | protected final File file;
43 | protected final String fileName;
44 | protected final String mimeType;
45 |
46 | public FileUploadable(final File file) {
47 | this.file = file;
48 | this.fileName = FileNameUtil.getName(file.getName());
49 | this.mimeType = null;
50 | }
51 |
52 | public FileUploadable(final File file, final String fileName, final String mimeType) {
53 | this.file = file;
54 | this.fileName = fileName;
55 | this.mimeType = mimeType;
56 | }
57 |
58 | @Override
59 | public File getContent() {
60 | return file;
61 | }
62 |
63 | @Override
64 | public byte[] getBytes() {
65 | try {
66 | return FileUtil.readBytes(file);
67 | } catch (IOException ioex) {
68 | throw new HttpException(ioex);
69 | }
70 | }
71 |
72 | @Override
73 | public String getFileName() {
74 | return fileName;
75 | }
76 |
77 | @Override
78 | public String getMimeType() {
79 | return mimeType;
80 | }
81 |
82 | @Override
83 | public int getSize() {
84 | return (int) file.length();
85 | }
86 |
87 | @Override
88 | public InputStream openInputStream() throws IOException {
89 | return new FileInputStream(file);
90 | }
91 | }
92 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/MultipartRequestInputStream.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload;
27 |
28 | import java.io.BufferedInputStream;
29 | import java.io.ByteArrayOutputStream;
30 | import java.io.IOException;
31 | import java.io.InputStream;
32 | import java.io.OutputStream;
33 |
34 | /**
35 | * Extended input stream based on buffered requests input stream.
36 | * It provides some more functions that might be useful when working
37 | * with uploaded fies.
38 | */
39 | public class MultipartRequestInputStream extends BufferedInputStream {
40 |
41 | public MultipartRequestInputStream(final InputStream in) {
42 | super(in);
43 | }
44 |
45 | /**
46 | * Reads expected byte. Throws exception on streams end.
47 | */
48 | public byte readByte() throws IOException {
49 | final int i = super.read();
50 | if (i == -1) {
51 | throw new IOException("End of HTTP request stream reached");
52 | }
53 | return (byte) i;
54 | }
55 |
56 | /**
57 | * Skips specified number of bytes.
58 | */
59 | public void skipBytes(final int i) throws IOException {
60 | final long len = super.skip(i);
61 | if (len != i) {
62 | throw new IOException("Failed to skip data in HTTP request");
63 | }
64 | }
65 |
66 | // ---------------------------------------------------------------- boundary
67 |
68 | protected byte[] boundary;
69 |
70 | /**
71 | * Reads boundary from the input stream.
72 | */
73 | public byte[] readBoundary() throws IOException {
74 | final ByteArrayOutputStream boundaryOutput = new ByteArrayOutputStream();
75 | byte b;
76 | // skip optional whitespaces
77 | while ((b = readByte()) <= ' ') {
78 | }
79 | boundaryOutput.write(b);
80 |
81 | // now read boundary chars
82 | while ((b = readByte()) != '\r') {
83 | boundaryOutput.write(b);
84 | }
85 | if (boundaryOutput.size() == 0) {
86 | throw new IOException("Problems with parsing request: invalid boundary");
87 | }
88 | skipBytes(1);
89 | boundary = new byte[boundaryOutput.size() + 2];
90 | System.arraycopy(boundaryOutput.toByteArray(), 0, boundary, 2, boundary.length - 2);
91 | boundary[0] = '\r';
92 | boundary[1] = '\n';
93 | return boundary;
94 | }
95 |
96 | // ---------------------------------------------------------------- data header
97 |
98 | protected FileUploadHeader lastHeader;
99 |
100 | public FileUploadHeader getLastHeader() {
101 | return lastHeader;
102 | }
103 |
104 | /**
105 | * Reads data header from the input stream. When there is no more
106 | * headers (i.e. end of stream reached), returns null
107 | */
108 | public FileUploadHeader readDataHeader(final String encoding) throws IOException {
109 | final String dataHeader = readDataHeaderString(encoding);
110 | if (dataHeader != null) {
111 | lastHeader = new FileUploadHeader(dataHeader);
112 | } else {
113 | lastHeader = null;
114 | }
115 | return lastHeader;
116 | }
117 |
118 |
119 | protected String readDataHeaderString(final String encoding) throws IOException {
120 | final ByteArrayOutputStream data = new ByteArrayOutputStream();
121 | byte b;
122 | while (true) {
123 | // end marker byte on offset +0 and +2 must be 13
124 | if ((b = readByte()) != '\r') {
125 | data.write(b);
126 | continue;
127 | }
128 | mark(4);
129 | skipBytes(1);
130 | final int i = read();
131 | if (i == -1) {
132 | // reached end of stream
133 | return null;
134 | }
135 | if (i == '\r') {
136 | reset();
137 | break;
138 | }
139 | reset();
140 | data.write(b);
141 | }
142 | skipBytes(3);
143 | if (encoding != null) {
144 | return data.toString(encoding);
145 | } else {
146 | return data.toString();
147 | }
148 | }
149 |
150 |
151 | // ---------------------------------------------------------------- copy
152 |
153 | /**
154 | * Copies bytes from this stream to some output until boundary is
155 | * reached. Returns number of copied bytes. It will throw an exception
156 | * for any irregular behaviour.
157 | */
158 | public int copyAll(final OutputStream out) throws IOException {
159 | int count = 0;
160 | while (true) {
161 | final byte b = readByte();
162 | if (isBoundary(b)) {
163 | break;
164 | }
165 | out.write(b);
166 | count++;
167 | }
168 | return count;
169 | }
170 |
171 | /**
172 | * Copies max or less number of bytes to output stream. Useful for determining
173 | * if uploaded file is larger then expected.
174 | */
175 | public int copyMax(final OutputStream out, final int maxBytes) throws IOException {
176 | int count = 0;
177 | while (true) {
178 | final byte b = readByte();
179 | if (isBoundary(b)) {
180 | break;
181 | }
182 | out.write(b);
183 | count++;
184 | if (count == maxBytes) {
185 | return count;
186 | }
187 | }
188 | return count;
189 | }
190 |
191 | /**
192 | * Skips to the boundary and returns total number of bytes skipped.
193 | */
194 | public int skipToBoundary() throws IOException {
195 | int count = 0;
196 | while (true) {
197 | final byte b = readByte();
198 | count++;
199 | if (isBoundary(b)) {
200 | break;
201 | }
202 | }
203 | return count;
204 | }
205 |
206 | /**
207 | * Checks if the current byte (i.e. one that was read last) represents
208 | * the very first byte of the boundary.
209 | */
210 | public boolean isBoundary(byte b) throws IOException {
211 | final int boundaryLen = boundary.length;
212 | mark(boundaryLen + 1);
213 | int bpos = 0;
214 | while (b == boundary[bpos]) {
215 | b = readByte();
216 | bpos++;
217 | if (bpos == boundaryLen) {
218 | return true; // boundary found!
219 | }
220 | }
221 | reset();
222 | return false;
223 | }
224 | }
225 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/Uploadable.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload;
27 |
28 | import java.io.IOException;
29 | import java.io.InputStream;
30 |
31 | /**
32 | * Common interface of uploaded content for {@link jodd.http.HttpBase#form() form parameters}.
33 | * All supported objects that can be uploaded using
34 | * the {@link jodd.http.HttpBase#form(String, Object)} has to
35 | * be wrapped with this interface.
36 | */
37 | public interface Uploadable {
38 |
39 | /**
40 | * Returns the original content.
41 | */
42 | public T getContent();
43 |
44 | /**
45 | * Returns content bytes.
46 | */
47 | public byte[] getBytes();
48 |
49 | /**
50 | * Returns content file name.
51 | * If null
, the field's name will be used.
52 | */
53 | public String getFileName();
54 |
55 | /**
56 | * Returns MIME type. If null
,
57 | * MIME type will be determined from
58 | * {@link #getFileName() file name's} extension.
59 | */
60 | public String getMimeType();
61 |
62 | /**
63 | * Returns size in bytes.
64 | */
65 | public int getSize();
66 |
67 | /**
68 | * Opens InputStream
. User is responsible
69 | * for closing it.
70 | */
71 | public InputStream openInputStream() throws IOException;
72 |
73 | }
74 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/impl/AdaptiveFileUploadFactory.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload.impl;
27 |
28 | import jodd.http.upload.FileUpload;
29 | import jodd.http.upload.FileUploadFactory;
30 | import jodd.http.upload.MultipartRequestInputStream;
31 |
32 | import java.io.File;
33 |
34 | /**
35 | *
36 | * Factory for {@link AdaptiveFileUpload}.
37 | */
38 | public class AdaptiveFileUploadFactory implements FileUploadFactory {
39 |
40 | protected int memoryThreshold = 8192;
41 | protected File uploadPath;
42 | protected int maxFileSize = 102400;
43 | protected boolean breakOnError;
44 | protected String[] fileExtensions;
45 | protected boolean allowFileExtensions = true;
46 |
47 | /**
48 | * {@inheritDoc}
49 | */
50 | @Override
51 | public FileUpload create(final MultipartRequestInputStream input) {
52 | return new AdaptiveFileUpload(input, memoryThreshold, uploadPath, maxFileSize, breakOnError, fileExtensions, allowFileExtensions);
53 | }
54 |
55 | // ---------------------------------------------------------------- properties
56 |
57 | public int getMemoryThreshold() {
58 | return memoryThreshold;
59 | }
60 | /**
61 | * Specifies per file memory limit for keeping uploaded files in the memory.
62 | */
63 | public AdaptiveFileUploadFactory setMemoryThreshold(final int memoryThreshold) {
64 | if (memoryThreshold >= 0) {
65 | this.memoryThreshold = memoryThreshold;
66 | }
67 | return this;
68 | }
69 |
70 | public File getUploadPath() {
71 | return uploadPath;
72 | }
73 |
74 | /**
75 | * Specifies the upload path. If set to null
default
76 | * system TEMP path will be used.
77 | */
78 | public AdaptiveFileUploadFactory setUploadPath(final File uploadPath) {
79 | this.uploadPath = uploadPath;
80 | return this;
81 | }
82 |
83 | public int getMaxFileSize() {
84 | return maxFileSize;
85 | }
86 |
87 | /**
88 | * Sets maximum file upload size. Setting to -1
89 | * disables this constraint.
90 | */
91 | public AdaptiveFileUploadFactory setMaxFileSize(final int maxFileSize) {
92 | this.maxFileSize = maxFileSize;
93 | return this;
94 | }
95 |
96 | public boolean isBreakOnError() {
97 | return breakOnError;
98 | }
99 |
100 | public AdaptiveFileUploadFactory setBreakOnError(final boolean breakOnError) {
101 | this.breakOnError = breakOnError;
102 | return this;
103 | }
104 |
105 | /**
106 | * Specifies if upload should break on error.
107 | */
108 | public AdaptiveFileUploadFactory breakOnError(final boolean breakOnError) {
109 | this.breakOnError = breakOnError;
110 | return this;
111 | }
112 |
113 | /**
114 | * Allow or disallow set of file extensions. Only one rule can be active at time,
115 | * which means user can only specify extensions that are either allowed or disallowed.
116 | * Setting this value to null
will turn this feature off.
117 | */
118 | public AdaptiveFileUploadFactory setFileExtensions(final String[] fileExtensions, final boolean allow) {
119 | this.fileExtensions = fileExtensions;
120 | this.allowFileExtensions = allow;
121 | return this;
122 | }
123 |
124 | }
125 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/impl/DiskFileUpload.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload.impl;
27 |
28 | import jodd.http.upload.FileUpload;
29 | import jodd.http.upload.MultipartRequestInputStream;
30 | import jodd.io.FileUtil;
31 | import jodd.io.IOUtil;
32 |
33 | import java.io.BufferedInputStream;
34 | import java.io.BufferedOutputStream;
35 | import java.io.File;
36 | import java.io.FileInputStream;
37 | import java.io.FileOutputStream;
38 | import java.io.IOException;
39 | import java.io.InputStream;
40 | import java.io.OutputStream;
41 |
42 | /**
43 | * {@link FileUpload} that saves uploaded files directly to destination folder.
44 | */
45 | public class DiskFileUpload extends FileUpload {
46 |
47 | protected final File destFolder;
48 |
49 | DiskFileUpload(final MultipartRequestInputStream input, final File destinationFolder, final int maxFileSize) {
50 | super(input, maxFileSize);
51 | this.destFolder = destinationFolder;
52 | }
53 |
54 | /**
55 | * Returns false
as uploaded file is stored on disk.
56 | */
57 | @Override
58 | public boolean isInMemory() {
59 | return false;
60 | }
61 |
62 | /**
63 | * Returns destination folder.
64 | */
65 | public File getDestinationFolder() {
66 | return destFolder;
67 | }
68 |
69 | /**
70 | * Returns uploaded and saved file.
71 | */
72 | public File getFile() {
73 | return file;
74 | }
75 |
76 | protected File file;
77 |
78 | /**
79 | * Returns files content from disk file.
80 | * If error occurs, it returns null
81 | */
82 | @Override
83 | public byte[] getFileContent() throws IOException {
84 | return FileUtil.readBytes(file);
85 | }
86 |
87 | /**
88 | * Returns new buffered file input stream.
89 | */
90 | @Override
91 | public InputStream getFileInputStream() throws IOException {
92 | return new BufferedInputStream(new FileInputStream(file));
93 | }
94 |
95 | @Override
96 | protected void processStream() throws IOException {
97 | file = new File(destFolder, header.getFileName());
98 | final OutputStream out = new BufferedOutputStream(new FileOutputStream(file));
99 |
100 | size = 0;
101 | try {
102 | if (maxFileSize == -1) {
103 | size = input.copyAll(out);
104 | } else {
105 | size = input.copyMax(out, maxFileSize + 1); // one more byte to detect larger files
106 | if (size > maxFileSize) {
107 | fileTooBig = true;
108 | valid = false;
109 | input.skipToBoundary();
110 | return;
111 | }
112 | }
113 | valid = true;
114 | } finally {
115 | IOUtil.close(out);
116 | }
117 | }
118 |
119 | }
120 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/impl/DiskFileUploadFactory.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload.impl;
27 |
28 | import jodd.http.upload.FileUpload;
29 | import jodd.http.upload.FileUploadFactory;
30 | import jodd.http.upload.MultipartRequestInputStream;
31 | import jodd.util.SystemUtil;
32 |
33 | import java.io.File;
34 | import java.io.IOException;
35 |
36 | /**
37 | * Factory for {@link jodd.http.upload.impl.DiskFileUpload}
38 | */
39 | public class DiskFileUploadFactory implements FileUploadFactory {
40 |
41 | protected File destFolder;
42 |
43 | protected int maxFileSize = 102400;
44 |
45 | public DiskFileUploadFactory() throws IOException {
46 | this(SystemUtil.info().getTempDir());
47 | }
48 |
49 | public DiskFileUploadFactory(final String destFolder) throws IOException {
50 | this(destFolder, 102400);
51 |
52 | }
53 |
54 | public DiskFileUploadFactory(final String destFolder, final int maxFileSize) throws IOException {
55 | setUploadDir(destFolder);
56 | this.maxFileSize = maxFileSize;
57 | }
58 |
59 |
60 | public DiskFileUploadFactory setUploadDir(String destFolder) throws IOException {
61 | if (destFolder == null) {
62 | destFolder = SystemUtil.info().getTempDir();
63 | }
64 | final File destination = new File(destFolder);
65 | if (!destination.exists()) {
66 | destination.mkdirs();
67 | }
68 | if (!destination.isDirectory()) {
69 | throw new IOException("Invalid destination folder: " + destFolder);
70 | }
71 | this.destFolder = destination;
72 | return this;
73 | }
74 |
75 | public int getMaxFileSize() {
76 | return maxFileSize;
77 | }
78 |
79 | /**
80 | * Sets maximum file upload size. Setting to -1 will disable this constraint.
81 | */
82 | public DiskFileUploadFactory setMaxFileSize(final int maxFileSize) {
83 | this.maxFileSize = maxFileSize;
84 | return this;
85 | }
86 |
87 | /**
88 | * {@inheritDoc}
89 | */
90 | @Override
91 | public FileUpload create(final MultipartRequestInputStream input) {
92 | return new DiskFileUpload(input, destFolder, maxFileSize);
93 | }
94 |
95 | }
96 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/impl/MemoryFileUpload.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload.impl;
27 |
28 |
29 | import jodd.http.upload.FileUpload;
30 | import jodd.http.upload.MultipartRequestInputStream;
31 |
32 | import java.io.ByteArrayInputStream;
33 | import java.io.ByteArrayOutputStream;
34 | import java.io.IOException;
35 | import java.io.InputStream;
36 |
37 | /**
38 | * {@link FileUpload} that stores uploaded files in memory byte array.
39 | */
40 | public class MemoryFileUpload extends FileUpload {
41 |
42 | MemoryFileUpload(final MultipartRequestInputStream input, final int maxFileSize) {
43 | super(input, maxFileSize);
44 | }
45 |
46 | // ---------------------------------------------------------------- logic
47 |
48 | protected byte[] data;
49 |
50 | /**
51 | * Returns byte array containing uploaded file data.
52 | */
53 | @Override
54 | public byte[] getFileContent() {
55 | return data;
56 | }
57 |
58 | /**
59 | * Returns true
as uploaded file is stored in memory.
60 | */
61 | @Override
62 | public boolean isInMemory() {
63 | return true;
64 | }
65 |
66 | /**
67 | * Returns byte array input stream.
68 | */
69 | @Override
70 | public InputStream getFileInputStream() {
71 | return new ByteArrayInputStream(data);
72 | }
73 |
74 | /**
75 | * Reads data from input stream into byte array and stores file size.
76 | */
77 | @Override
78 | public void processStream() throws IOException {
79 | final ByteArrayOutputStream out = new ByteArrayOutputStream();
80 | size = 0;
81 | if (maxFileSize == -1) {
82 | size += input.copyAll(out);
83 | } else {
84 | size += input.copyMax(out, maxFileSize + 1); // one more byte to detect larger files
85 | if (size > maxFileSize) {
86 | fileTooBig = true;
87 | valid = false;
88 | input.skipToBoundary();
89 | return;
90 | }
91 | }
92 | data = out.toByteArray();
93 | size = data.length;
94 | valid = true;
95 | }
96 |
97 | }
98 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/impl/MemoryFileUploadFactory.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.upload.impl;
27 |
28 | import jodd.http.upload.FileUpload;
29 | import jodd.http.upload.FileUploadFactory;
30 | import jodd.http.upload.MultipartRequestInputStream;
31 |
32 | /**
33 | * Factory for {@link jodd.net.upload.impl.MemoryFileUpload}.
34 | */
35 | public class MemoryFileUploadFactory implements FileUploadFactory {
36 |
37 | protected int maxFileSize = 102400;
38 |
39 | public int getMaxFileSize() {
40 | return maxFileSize;
41 | }
42 |
43 | /**
44 | * Sets maximum file upload size. Setting to -1 will disable this constraint.
45 | */
46 | public MemoryFileUploadFactory setMaxFileSize(final int maxFileSize) {
47 | this.maxFileSize = maxFileSize;
48 | return this;
49 | }
50 |
51 | /**
52 | * {@inheritDoc}
53 | */
54 | @Override
55 | public FileUpload create(final MultipartRequestInputStream input) {
56 | return new MemoryFileUpload(input, maxFileSize);
57 | }
58 |
59 | }
60 |
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/impl/package-info.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | /**
27 | * Various implementations of uploaded files and their factories.
28 | */
29 | package jodd.io.upload.impl;
--------------------------------------------------------------------------------
/src/main/java/jodd/http/upload/package-info.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | /**
27 | * Uploadable content and few implementations.
28 | */
29 | package jodd.http.upload;
30 |
--------------------------------------------------------------------------------
/src/main/resources/META-INF/LICENSE:
--------------------------------------------------------------------------------
1 | Copyright (c) 2003-present, Jodd Team (https://jodd.org)
2 | All rights reserved.
3 |
4 | Redistribution and use in source and binary forms, with or without
5 | modification, are permitted provided that the following conditions are met:
6 |
7 | 1. Redistributions of source code must retain the above copyright notice,
8 | this list of conditions and the following disclaimer.
9 |
10 | 2. Redistributions in binary form must reproduce the above copyright
11 | notice, this list of conditions and the following disclaimer in the
12 | documentation and/or other materials provided with the distribution.
13 |
14 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | POSSIBILITY OF SUCH DAMAGE.
25 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/CRLFInjectionTest.java:
--------------------------------------------------------------------------------
1 | package jodd.http;
2 |
3 | import jodd.net.URLCoder;
4 | import org.junit.jupiter.api.Test;
5 |
6 | import static org.junit.jupiter.api.Assertions.assertEquals;
7 |
8 | class CRLFInjectionTest {
9 |
10 | @Test
11 | void testGet_crlf_injection() {
12 | String url = "http://127.0.0.1:6379/ \rfoo";//"HTTP/1.1\r\nHost: 127.0.0.13:1099\r\n\r\nSLAVE OF inhann.top:6379\r\n\r\nPOST / ";
13 | HttpRequest req = HttpRequest.get(url);
14 |
15 | assertEquals("GET /%20%0Dfoo HTTP/1.1", req.toString().split("\n")[0].trim());
16 | }
17 |
18 | @Test
19 | void testGet_crlf_injection_path() {
20 | String url = "http://127.0.0.1:6379/";
21 | HttpRequest req = HttpRequest.get(url).path(" \rfoo");
22 |
23 | assertEquals("GET /%20%0Dfoo HTTP/1.1", req.toString().split("\n")[0].trim());
24 | }
25 |
26 | @Test
27 | void testGet_crlf_injection2() {
28 | String path = " HTTP/1.1\n" +
29 | "Host: 127.0.0.13:1099\n" +
30 | "\n" +
31 | "SLAVE OF inhann.top:6379\n" +
32 | "\n" +
33 | "POST /";
34 | String url = "http://127.0.0.1:6379/" + path;
35 | HttpRequest req = HttpRequest.get(url);
36 |
37 | assertEquals("GET /" + URLCoder.encodePath(path) + " HTTP/1.1", req.toString().split("\n")[0].trim());
38 | }
39 |
40 | }
41 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/CookieTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.Test;
29 |
30 | import static org.junit.jupiter.api.Assertions.assertEquals;
31 | import static org.junit.jupiter.api.Assertions.assertTrue;
32 |
33 | class CookieTest {
34 |
35 | @Test
36 | void testCookieParsing() {
37 | Cookie cookie = new Cookie("name=value");
38 |
39 | assertEquals("name", cookie.getName());
40 | assertEquals("value", cookie.getValue());
41 | assertEquals(null, cookie.getExpires());
42 |
43 | cookie = new Cookie("name2=value2; Expires=Wed, 09 Jun 2021 10:18:14 GMT");
44 |
45 | assertEquals("name2", cookie.getName());
46 | assertEquals("value2", cookie.getValue());
47 | assertEquals("Wed, 09 Jun 2021 10:18:14 GMT", cookie.getExpires());
48 |
49 | cookie = new Cookie("LSID=DQAAAEaem_vYg; Path=/accounts; Secure; Expires=Wed, 13 Jan 2021 22:23:01 GMT; HttpOnly");
50 |
51 | assertEquals("LSID", cookie.getName());
52 | assertEquals("DQAAAEaem_vYg", cookie.getValue());
53 | assertEquals("/accounts", cookie.getPath());
54 | assertTrue(cookie.isSecure());
55 | assertTrue(cookie.isHttpOnly());
56 | }
57 |
58 | @Test
59 | void test395() {
60 | Cookie cookie = new Cookie("name=value;");
61 |
62 | assertEquals("name", cookie.getName());
63 | assertEquals("value", cookie.getValue());
64 |
65 | cookie = new Cookie("name=value; ");
66 |
67 | assertEquals("name", cookie.getName());
68 | assertEquals("value", cookie.getValue());
69 |
70 | cookie = new Cookie("p_skey=UIJeeZgODkPQgiVcwHJBhq9mYrZC9JdpYF6SCZ3fNfY_; PATH=/; DOMAIN=mail.qq.com; ;");
71 |
72 | assertEquals("p_skey", cookie.getName());
73 | assertEquals("UIJeeZgODkPQgiVcwHJBhq9mYrZC9JdpYF6SCZ3fNfY_", cookie.getValue());
74 | }
75 |
76 | @Test
77 | void testSpecialCookieValues() {
78 | Cookie cookie = new Cookie("name=value");
79 |
80 | assertEquals("name", cookie.getName());
81 | assertEquals("value", cookie.getValue());
82 |
83 | cookie = new Cookie("name=value;");
84 |
85 | assertEquals("name", cookie.getName());
86 | assertEquals("value", cookie.getValue());
87 |
88 | // duplicated value
89 |
90 | cookie = new Cookie("name=value;a=b;");
91 |
92 | assertEquals("name", cookie.getName());
93 | assertEquals("value", cookie.getValue());
94 |
95 | // empty value
96 |
97 | cookie = new Cookie("name=");
98 |
99 | assertEquals("name", cookie.getName());
100 | assertEquals("", cookie.getValue());
101 |
102 | // empty name
103 |
104 | cookie = new Cookie("=value");
105 |
106 | assertEquals(null, cookie.getName());
107 | assertEquals(null, cookie.getValue());
108 | }
109 |
110 | @Test
111 | void testSetGetCookieFromRequest() {
112 | final HttpRequest request = new HttpRequest();
113 | request.cookies(new Cookie("one", "two"), new Cookie("one2", "two2"));
114 |
115 | final Cookie[] cookies = request.cookies();
116 | assertEquals(2, cookies.length);
117 |
118 | assertEquals("one", cookies[0].getName());
119 | assertEquals("two", cookies[0].getValue());
120 |
121 | assertEquals("one2", cookies[1].getName());
122 | assertEquals("two2", cookies[1].getValue());
123 |
124 | }
125 | }
126 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/EchoTestServer.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import java.io.File;
29 | import java.io.IOException;
30 | import java.util.Properties;
31 |
32 | public class EchoTestServer extends NanoHTTPD {
33 |
34 | public EchoTestServer() throws IOException {
35 | super(8081, new File("."));
36 | }
37 |
38 | public String uri;
39 |
40 | public String method;
41 |
42 | public Properties header;
43 |
44 | public Properties params;
45 |
46 | public Properties files;
47 |
48 | public Response serve(String uri, String method, Properties header, Properties parms, Properties files) {
49 | String msg = method + " " + uri;
50 |
51 | this.uri = uri;
52 | this.method = method;
53 | this.header = header;
54 | this.params = parms;
55 | this.files = files;
56 |
57 | return new NanoHTTPD.Response(HTTP_OK, MIME_HTML, msg);
58 | }
59 | }
--------------------------------------------------------------------------------
/src/test/java/jodd/http/FragmentTest.java:
--------------------------------------------------------------------------------
1 | package jodd.http;
2 |
3 | import org.junit.jupiter.api.Test;
4 |
5 | import static org.junit.jupiter.api.Assertions.assertEquals;
6 |
7 | class FragmentTest {
8 |
9 | @Test
10 | void testFragment() {
11 | final HttpRequest request = HttpRequest.get("https://studioharrison.com/#product-group");
12 |
13 | assertEquals("/", request.path);
14 | assertEquals("product-group", request.fragment());
15 |
16 | assertEquals("https://studioharrison.com/#product-group", request.url());
17 | }
18 |
19 | @Test
20 | void testFragmentWithQuery() {
21 | final HttpRequest request = HttpRequest.get("https://studioharrison.com/foo?me=1#foo");
22 |
23 | assertEquals("/foo", request.path);
24 | assertEquals("foo", request.fragment());
25 |
26 | assertEquals("https://studioharrison.com/foo?me=1#foo", request.url());
27 | }
28 | }
29 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/GoogleMapsTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.io.FileUtil;
29 | import org.junit.jupiter.api.Test;
30 |
31 | import java.io.ByteArrayInputStream;
32 | import java.io.IOException;
33 | import java.net.URL;
34 |
35 | import static org.junit.jupiter.api.Assertions.assertEquals;
36 | import static org.junit.jupiter.api.Assertions.fail;
37 |
38 | class GoogleMapsTest {
39 |
40 | @Test
41 | void testNoBody() throws IOException {
42 | /*HttpResponse httpResponse = HttpRequest.get("http://maps.googleapis.com/maps/api/geocode/json")
43 | .query("address", "14621")
44 | .query("sensor", "false")
45 | .send();
46 | */
47 | URL data = RawTest.class.getResource("2-response.txt");
48 | byte[] fileContent = FileUtil.readBytes(data.getFile());
49 |
50 | HttpResponse httpResponse = HttpResponse.readFrom(new ByteArrayInputStream(fileContent));
51 |
52 | try {
53 | httpResponse.bodyText();
54 | } catch (Exception ex) {
55 | fail(ex.toString());
56 | }
57 |
58 | assertEquals("", httpResponse.bodyText());
59 | }
60 |
61 | @Test
62 | void testNoContentLength() throws IOException {
63 | URL data = RawTest.class.getResource("3-response.txt");
64 | byte[] fileContent = FileUtil.readBytes(data.getFile());
65 |
66 | HttpResponse httpResponse = HttpResponse.readFrom(new ByteArrayInputStream(fileContent));
67 |
68 | assertEquals("Body!", httpResponse.bodyText());
69 | }
70 |
71 | }
72 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpConnectionTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.http.upload.ByteArrayUploadable;
29 | import jodd.io.FileUtil;
30 | import jodd.net.MimeTypes;
31 | import jodd.util.StringUtil;
32 | import org.junit.jupiter.api.Test;
33 |
34 | import java.io.File;
35 | import java.io.IOException;
36 | import java.nio.charset.StandardCharsets;
37 |
38 | import static org.junit.jupiter.api.Assertions.assertEquals;
39 | import static org.junit.jupiter.api.Assertions.assertNotNull;
40 |
41 | class HttpConnectionTest {
42 |
43 | @Test
44 | void testEcho() throws IOException {
45 | final EchoTestServer echoTestServer = new EchoTestServer();
46 |
47 | final HttpResponse response = HttpRequest.get("http://localhost:8081/hello?id=12").send();
48 |
49 | assertEquals(200, response.statusCode());
50 | assertEquals("OK", response.statusPhrase());
51 |
52 | assertEquals("GET", echoTestServer.method);
53 | assertEquals("/hello", echoTestServer.uri);
54 | assertEquals(1, echoTestServer.params.size());
55 | assertEquals("12", echoTestServer.params.get("id"));
56 |
57 | assertEquals("GET /hello", response.bodyRaw());
58 |
59 | echoTestServer.stop();
60 | }
61 |
62 | @Test
63 | void testUpload() throws IOException {
64 | final EchoTestServer echoTestServer = new EchoTestServer();
65 |
66 | final File file = FileUtil.createTempFile();
67 | file.deleteOnExit();
68 |
69 | FileUtil.writeString(file, "upload тест");
70 | assertEquals("upload тест", FileUtil.readString(file));
71 |
72 | final HttpResponse response = HttpRequest
73 | .post("http://localhost:8081/hello")
74 | .form("id", "12")
75 | .form("file", file)
76 | .send();
77 |
78 | assertEquals(200, response.statusCode());
79 | assertEquals("OK", response.statusPhrase());
80 |
81 | assertEquals("POST", echoTestServer.method);
82 | assertEquals("12", echoTestServer.params.get("id"));
83 | final File uploadedFile = new File(echoTestServer.files.get("file").toString());
84 | assertNotNull(uploadedFile);
85 | assertEquals("upload тест", FileUtil.readString(uploadedFile));
86 |
87 | assertEquals("POST /hello", response.bodyRaw());
88 |
89 | echoTestServer.stop();
90 | file.delete();
91 | }
92 |
93 | @Test
94 | void testUploadWithUploadable() throws IOException {
95 | final EchoTestServer echoTestServer = new EchoTestServer();
96 |
97 | final HttpResponse response = HttpRequest
98 | .post("http://localhost:8081/hello")
99 | .multipart(true)
100 | .form("id", "12")
101 | .form("file", new ByteArrayUploadable(
102 | "upload тест".getBytes(StandardCharsets.UTF_8), "d ст", MimeTypes.MIME_TEXT_PLAIN))
103 | .send();
104 |
105 | assertEquals(200, response.statusCode());
106 | assertEquals("OK", response.statusPhrase());
107 |
108 | assertEquals("POST", echoTestServer.method);
109 | assertEquals("12", echoTestServer.params.get("id"));
110 | final File uploadedFile = new File(echoTestServer.files.get("file").toString());
111 | assertNotNull(uploadedFile);
112 | assertEquals("upload тест", FileUtil.readString(uploadedFile));
113 |
114 | assertEquals("POST /hello", response.bodyRaw());
115 |
116 | echoTestServer.stop();
117 | }
118 |
119 | @Test
120 | void testUploadWithMonitor() throws IOException {
121 | final EchoTestServer echoTestServer = new EchoTestServer();
122 |
123 | final File file = FileUtil.createTempFile();
124 | file.deleteOnExit();
125 |
126 | FileUtil.writeString(file, StringUtil.repeat('A', 1024));
127 |
128 | final StringBuilder sb = new StringBuilder();
129 |
130 | final HttpResponse response = HttpRequest
131 | .post("http://localhost:8081/hello")
132 | .form("id", "12")
133 | .form("file", file)
134 | .monitor(new HttpProgressListener() {
135 | @Override
136 | public void transferred(final int len) {
137 | sb.append(":").append(len);
138 | }
139 | })
140 | .send();
141 |
142 | assertEquals(200, response.statusCode());
143 | assertEquals("OK", response.statusPhrase());
144 |
145 | echoTestServer.stop();
146 | file.delete();
147 |
148 | assertEquals(":0:512:1024:148", StringUtil.substring(sb.toString(), 0, -1));
149 | }
150 |
151 | }
152 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpHeaderTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.Test;
29 |
30 | import static org.junit.jupiter.api.Assertions.assertEquals;
31 | import static org.junit.jupiter.api.Assertions.assertTrue;
32 |
33 | public class HttpHeaderTest {
34 |
35 | @Test
36 | void testSettingHostsHeader_changeWithSet() {
37 | final HttpRequest httpRequest = HttpRequest.post("jodd.site");
38 |
39 | assertEquals("jodd.site", httpRequest.host());
40 | // calling toString as it will set the HEADER
41 | assertTrue(httpRequest.toString().contains("jodd.site"));
42 |
43 | assertEquals("jodd.site", httpRequest.header(HttpRequest.HEADER_HOST));
44 |
45 | // change
46 | httpRequest.set("oblac.rs");
47 |
48 | // is the header changed? first check the header
49 | assertEquals("oblac.rs", httpRequest.host());
50 | assertEquals("oblac.rs", httpRequest.header(HttpRequest.HEADER_HOST));
51 | // the regenerated request should work
52 | assertTrue(httpRequest.toString().contains("oblac.rs"));
53 | // after the generation
54 | assertEquals("oblac.rs", httpRequest.header(HttpRequest.HEADER_HOST));
55 | }
56 |
57 | @Test
58 | void testSettingHostsHeader_changeWithHost() {
59 | final HttpRequest httpRequest = HttpRequest.post("jodd.site");
60 |
61 | assertEquals("jodd.site", httpRequest.host());
62 | // calling toString as it will set the HEADER
63 | assertTrue(httpRequest.toString().contains("jodd.site"));
64 |
65 | assertEquals("jodd.site", httpRequest.header(HttpRequest.HEADER_HOST));
66 |
67 | // change
68 | httpRequest.host("oblac.rs");
69 |
70 | // is the header changed? first check the header
71 | assertEquals("oblac.rs", httpRequest.host());
72 | assertEquals("oblac.rs", httpRequest.header(HttpRequest.HEADER_HOST));
73 | // the regenerated request should work
74 | assertTrue(httpRequest.toString().contains("oblac.rs"));
75 | // after the generation
76 | assertEquals("oblac.rs", httpRequest.header(HttpRequest.HEADER_HOST));
77 | }
78 |
79 | }
80 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpMultiMapTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.Test;
29 |
30 | import java.util.Iterator;
31 | import java.util.List;
32 | import java.util.Map;
33 |
34 | import static org.junit.jupiter.api.Assertions.assertEquals;
35 | import static org.junit.jupiter.api.Assertions.assertFalse;
36 | import static org.junit.jupiter.api.Assertions.assertNull;
37 | import static org.junit.jupiter.api.Assertions.assertTrue;
38 | import static org.junit.jupiter.api.Assertions.fail;
39 |
40 | class HttpMultiMapTest {
41 |
42 | @Test
43 | void testAdd() {
44 | HttpMultiMap mm = HttpMultiMap.newCaseInsensitiveMap();
45 |
46 | mm.add("One", "one");
47 | mm.add("Two", "two");
48 |
49 | assertEquals(2, mm.size());
50 | assertEquals("one", mm.get("one"));
51 | assertEquals("two", mm.get("two"));
52 | }
53 |
54 | @Test
55 | void testAddSameName() {
56 | HttpMultiMap mm = HttpMultiMap.newCaseInsensitiveMap();
57 |
58 | mm.add("One", "one");
59 | mm.add("one", "two");
60 |
61 | assertEquals(1, mm.size());
62 | assertEquals("two", mm.get("one"));
63 |
64 | List all = mm.getAll("one");
65 | assertEquals(2, all.size());
66 | assertEquals("one", all.get(0));
67 | assertEquals("two", all.get(1));
68 |
69 | mm.add("one", "three");
70 | all = mm.getAll("one");
71 | assertEquals(3, all.size());
72 | assertEquals("one", all.get(0));
73 | assertEquals("two", all.get(1));
74 | assertEquals("three", all.get(2));
75 | }
76 |
77 | @Test
78 | void testMissing() {
79 | HttpMultiMap mm = HttpMultiMap.newCaseInsensitiveMap();
80 |
81 | assertNull(mm.get("xxx"));
82 | }
83 |
84 | @Test
85 | void testIterator() {
86 | HttpMultiMap mm = HttpMultiMap.newCaseInsensitiveMap();
87 |
88 | mm.add("One", "one");
89 | mm.add("one", "two");
90 | mm.add("two", "2.");
91 | mm.add("one", "three");
92 |
93 | assertEquals(2, mm.size());
94 |
95 | Iterator> i = mm.iterator();
96 |
97 | assertTrue(i.hasNext());
98 | assertEquals("one", i.next().getValue());
99 | assertEquals("two", i.next().getValue());
100 | assertEquals("2.", i.next().getValue());
101 | assertEquals("three", i.next().getValue());
102 | assertFalse(i.hasNext());
103 |
104 | try {
105 | i.next();
106 | fail("error");
107 | } catch (Exception ignore) {}
108 |
109 | mm.clear();
110 | i = mm.iterator();
111 | assertFalse(i.hasNext());
112 | }
113 |
114 |
115 | @Test
116 | void testNullValues() {
117 | HttpMultiMap hmm = HttpMultiMap.newCaseInsensitiveMap();
118 |
119 | assertFalse(hmm.contains("one"));
120 |
121 | hmm.add("one", null);
122 |
123 | assertNull(hmm.get("one"));
124 | assertTrue(hmm.contains("one"));
125 |
126 | hmm.add("one", null);
127 |
128 | assertNull(hmm.get("one"));
129 | assertTrue(hmm.contains("one"));
130 |
131 | hmm.set("one", "1");
132 |
133 | assertEquals("1", hmm.get("one"));
134 | assertTrue(hmm.contains("one"));
135 | }
136 |
137 | @Test
138 | void testParametersNumber() {
139 | HttpMultiMap hmm = HttpMultiMap.newCaseInsensitiveMap();
140 |
141 | for (int i = 0; i < 30; i++) {
142 | hmm.add(String.valueOf(i), "!" + i);
143 | }
144 |
145 | assertEquals(30, hmm.size());
146 | }
147 |
148 | @Test
149 | void testLetterCaseInsensitive() {
150 | HttpMultiMap mm = HttpMultiMap.newCaseInsensitiveMap();
151 |
152 | mm.add("one", "1.1");
153 | mm.add("one", "1.1.1");
154 | mm.add("One", "1.2");
155 |
156 | assertEquals(1, mm.size());
157 |
158 | assertEquals("1.2", mm.get("one"));
159 | assertEquals("1.2", mm.get("ONE"));
160 | assertEquals("1.2", mm.get("One"));
161 |
162 | List list = mm.getAll("ONE");
163 |
164 | assertEquals(3, list.size());
165 |
166 | assertEquals(1, mm.names().size());
167 | assertEquals(3, mm.entries().size());
168 | }
169 |
170 | @Test
171 | void testLetterCaseSensitive() {
172 | HttpMultiMap mm = HttpMultiMap.newCaseSensitiveMap();
173 |
174 | mm.add("one", "1.1");
175 | mm.add("one", "1.1.1");
176 | mm.add("One", "1.2");
177 |
178 | assertEquals(2, mm.size());
179 |
180 | assertEquals("1.1.1", mm.get("one"));
181 | assertNull(mm.get("ONE"));
182 | assertEquals("1.2", mm.get("One"));
183 |
184 | List list = mm.getAll("ONE");
185 | assertEquals(0, list.size());
186 |
187 | list = mm.getAll("one");
188 | assertEquals(2, list.size());
189 |
190 | assertEquals(2, mm.names().size());
191 | assertEquals(3, mm.entries().size());
192 | }
193 |
194 | }
195 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpProgressListenerTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.Test;
29 |
30 | import static org.junit.jupiter.api.Assertions.assertEquals;
31 |
32 | class HttpProgressListenerTest {
33 |
34 | @Test
35 | void testHttpProgressListener() {
36 | HttpProgressListener hpl = new HttpProgressListener() {
37 | @Override
38 | public void transferred(int len) {
39 |
40 | }
41 | };
42 |
43 | assertEquals(512, hpl.callbackSize(0));
44 | assertEquals(512, hpl.callbackSize(1000));
45 | assertEquals(512, hpl.callbackSize(51200));
46 | assertEquals(512, hpl.callbackSize(51201));
47 |
48 | assertEquals(1024, hpl.callbackSize(102400));
49 | assertEquals(1024, hpl.callbackSize(102401));
50 | assertEquals(1024, hpl.callbackSize(102449));
51 |
52 | assertEquals(1025, hpl.callbackSize(102450));
53 | assertEquals(1025, hpl.callbackSize(102499));
54 | assertEquals(1025, hpl.callbackSize(102500));
55 | }
56 | }
57 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpRedirectTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.AfterAll;
29 | import org.junit.jupiter.api.BeforeAll;
30 | import org.junit.jupiter.api.Test;
31 |
32 | import static org.junit.jupiter.api.Assertions.assertEquals;
33 | import static org.junit.jupiter.api.Assertions.assertNotNull;
34 |
35 | class HttpRedirectTest {
36 |
37 | static TestServer testServer;
38 |
39 | @BeforeAll
40 | static void startServer() throws Exception {
41 | testServer = new TomcatServer();
42 | testServer.start();
43 | }
44 |
45 | @AfterAll
46 | static void stopServer() throws Exception {
47 | testServer.stop();
48 | }
49 |
50 | @Test
51 | void testRedirect() {
52 | final HttpRequest httpRequest = HttpRequest.get("localhost:8173/redirect");
53 |
54 | HttpResponse httpResponse = httpRequest.send();
55 |
56 | assertEquals(302, httpResponse.statusCode);
57 |
58 | final HttpSession httpSession = new HttpSession();
59 |
60 | httpSession.sendRequest(
61 | HttpRequest.get("localhost:8173/redirect"));
62 |
63 | httpResponse = httpSession.getHttpResponse();
64 |
65 | assertNotNull(httpResponse);
66 | assertEquals("target!", httpResponse.bodyRaw());
67 | }
68 |
69 | }
70 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpSessionOfflineTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.Test;
29 |
30 | import static org.junit.jupiter.api.Assertions.assertEquals;
31 |
32 | class HttpSessionOfflineTest {
33 |
34 | @Test
35 | void testDefaultParameters() {
36 | HttpSession httpSession = new HttpSession();
37 | httpSession.setDefaultHeader("aaa", "123");
38 |
39 | HttpRequest request = HttpRequest.get("foo.com");
40 | request.header("bbb", "987");
41 |
42 | httpSession.addDefaultHeaders(request);
43 |
44 | assertEquals(4, request.headerNames().size());
45 | assertEquals("123", request.header("aaa"));
46 | assertEquals("987", request.header("bbb"));
47 | }
48 |
49 | @Test
50 | void testDefaultParametersOverwrite() {
51 | HttpSession httpSession = new HttpSession();
52 | httpSession.setDefaultHeader("aaa", "123");
53 |
54 | HttpRequest request = HttpRequest.get("foo.com");
55 | request.header("aaa", "987");
56 |
57 | httpSession.addDefaultHeaders(request);
58 |
59 | assertEquals(3, request.headerNames().size());
60 | assertEquals("987", request.header("aaa"));
61 | }
62 | }
63 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpSessionTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.AfterAll;
29 | import org.junit.jupiter.api.BeforeAll;
30 | import org.junit.jupiter.api.Test;
31 |
32 | import static org.junit.jupiter.api.Assertions.assertEquals;
33 | import static org.junit.jupiter.api.Assertions.assertNotNull;
34 |
35 | class HttpSessionTest {
36 |
37 | static TestServer testServer;
38 |
39 | @BeforeAll
40 | static void startServer() throws Exception {
41 | testServer = new TomcatServer();
42 | testServer.start();
43 | }
44 |
45 | @AfterAll
46 | static void stopServer() throws Exception {
47 | testServer.stop();
48 | }
49 |
50 | @Test
51 | void testSessions() {
52 | final HttpSession httpSession = new HttpSession();
53 |
54 | httpSession.sendRequest(
55 | HttpRequest
56 | .get("localhost:8173/echo?id=17")
57 | .cookies(new Cookie("waffle", "jam"))
58 | .bodyText("hello"));
59 |
60 | final HttpResponse httpResponse = httpSession.getHttpResponse();
61 |
62 | assertNotNull(httpResponse);
63 | assertEquals("hello", httpResponse.bodyRaw());
64 |
65 | final Cookie[] cookies = httpResponse.cookies();
66 | assertEquals(1, cookies.length);
67 |
68 | assertEquals("waffle", cookies[0].getName());
69 | assertEquals("jam!", cookies[0].getValue());
70 | }
71 |
72 | @Test
73 | void testSessionRedirect() {
74 | final HttpSession httpSession = new HttpSession();
75 |
76 | httpSession.sendRequest(HttpRequest.get("localhost:8173/redirect"));
77 |
78 | final HttpResponse httpResponse = httpSession.getHttpResponse();
79 |
80 | assertEquals(200, httpResponse.statusCode());
81 | assertEquals("target!", httpResponse.bodyRaw());
82 |
83 | }
84 |
85 | }
86 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpUploadTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.io.FileUtil;
29 | import org.junit.jupiter.api.AfterAll;
30 | import org.junit.jupiter.api.BeforeAll;
31 | import org.junit.jupiter.api.Test;
32 |
33 | import java.io.File;
34 | import java.io.IOException;
35 |
36 | import static org.junit.jupiter.api.Assertions.assertTrue;
37 |
38 | class HttpUploadTest {
39 |
40 | static TestServer testServer;
41 |
42 | @BeforeAll
43 | static void startServer() throws Exception {
44 | testServer = new TomcatServer();
45 | testServer.start();
46 | }
47 |
48 | @AfterAll
49 | static void stopServer() throws Exception {
50 | testServer.stop();
51 | }
52 |
53 |
54 | @Test
55 | void uploadTest() throws IOException {
56 | File temp1 = FileUtil.createTempFile();
57 | FileUtil.writeString(temp1, "Temp1 content");
58 | File temp2 = FileUtil.createTempFile();
59 | FileUtil.writeString(temp2, "Temp2 content");
60 |
61 | temp1.deleteOnExit();
62 | temp2.deleteOnExit();
63 |
64 | HttpRequest httpRequest = HttpRequest.post("localhost:8173/echo")
65 | .form(
66 | "title", "test",
67 | "description", "Upload test",
68 | "file1", temp1,
69 | "file2", temp2
70 | );
71 |
72 |
73 | HttpResponse httpResponse = httpRequest.send();
74 | String body = httpResponse.bodyText();
75 |
76 | assertTrue(body.contains("Temp1 content"));
77 | assertTrue(body.contains("Temp2 content"));
78 | }
79 | }
80 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/HttpsFactoryTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.http.net.SSLSocketHttpConnectionProvider;
29 | import org.junit.jupiter.api.Test;
30 |
31 | import javax.net.ssl.SSLSocketFactory;
32 | import java.io.IOException;
33 | import java.net.InetAddress;
34 | import java.net.Socket;
35 | import java.net.UnknownHostException;
36 | import java.util.concurrent.atomic.AtomicBoolean;
37 |
38 | import static org.junit.jupiter.api.Assertions.assertTrue;
39 |
40 | class HttpsFactoryTest {
41 |
42 | @Test
43 | void testCustomSSLSocketHttpConnectionProvider() {
44 | final AtomicBoolean atomicBoolean = new AtomicBoolean();
45 |
46 | final SSLSocketFactory sslSocketFactory = new SSLSocketFactory() {
47 | @Override
48 | public String[] getDefaultCipherSuites() {
49 | return new String[0];
50 | }
51 |
52 | @Override
53 | public String[] getSupportedCipherSuites() {
54 | return new String[0];
55 | }
56 |
57 | @Override
58 | public Socket createSocket(Socket socket, String s, int i, boolean b) throws IOException {
59 | atomicBoolean.set(true);
60 | return null;
61 | }
62 |
63 | @Override
64 | public Socket createSocket(String s, int i) throws IOException, UnknownHostException {
65 | atomicBoolean.set(true);
66 | return null;
67 | }
68 |
69 | @Override
70 | public Socket createSocket(String s, int i, InetAddress inetAddress, int i1) throws IOException, UnknownHostException {
71 | atomicBoolean.set(true);
72 | return null;
73 | }
74 |
75 | @Override
76 | public Socket createSocket(InetAddress inetAddress, int i) throws IOException {
77 | atomicBoolean.set(true);
78 | return null;
79 | }
80 |
81 | @Override
82 | public Socket createSocket(InetAddress inetAddress, int i, InetAddress inetAddress1, int i1) throws IOException {
83 | atomicBoolean.set(true);
84 | return null;
85 | }
86 | };
87 |
88 | try {
89 | HttpRequest.get("https://google.com")
90 | .withConnectionProvider(new SSLSocketHttpConnectionProvider(sslSocketFactory))
91 | .open();
92 | }
93 | catch (NullPointerException npe) {
94 | }
95 |
96 | assertTrue(atomicBoolean.get());
97 | }
98 | }
99 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/NoLocationTest.java:
--------------------------------------------------------------------------------
1 | package jodd.http;
2 |
3 | import jodd.http.fixture.StringHttpRequest;
4 | import org.junit.jupiter.api.Test;
5 |
6 |
7 | import static org.junit.jupiter.api.Assertions.assertEquals;
8 |
9 | class NoLocationTest {
10 |
11 | @Test
12 | void testNoLocationInResponse() {
13 | HttpRequest httpRequest = StringHttpRequest.create(
14 | "HTTP/1.1 302 OK\n" +
15 | "Connection: close\n" +
16 | "\n");
17 | HttpResponse response = httpRequest.followRedirects(true).send();
18 | assertEquals(302, response.statusCode());
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/ProxyTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import io.netty.handler.codec.http.HttpHeaders;
29 | import jodd.http.net.SocketHttpConnectionProvider;
30 | import org.junit.jupiter.api.AfterEach;
31 | import org.junit.jupiter.api.BeforeEach;
32 | import org.junit.jupiter.api.Disabled;
33 | import org.junit.jupiter.api.Test;
34 | import org.junit.jupiter.api.condition.EnabledOnOs;
35 | import org.junit.jupiter.api.condition.OS;
36 | import org.mockserver.integration.ClientAndProxy;
37 | import org.mockserver.integration.ClientAndServer;
38 | import org.mockserver.model.Header;
39 |
40 | import static org.junit.jupiter.api.Assertions.assertEquals;
41 | import static org.junit.jupiter.api.Assertions.assertTrue;
42 | import static org.mockserver.integration.ClientAndProxy.startClientAndProxy;
43 | import static org.mockserver.integration.ClientAndServer.startClientAndServer;
44 | import static org.mockserver.model.HttpRequest.request;
45 | import static org.mockserver.model.HttpResponse.response;
46 | import static org.mockserver.verify.VerificationTimes.exactly;
47 |
48 | class ProxyTest {
49 |
50 | private ClientAndProxy proxy;
51 | private ClientAndServer mockServer;
52 |
53 | @BeforeEach
54 | void startProxy() {
55 | mockServer = startClientAndServer(1080);
56 | proxy = startClientAndProxy(1090);
57 | setupMockServer();
58 | }
59 |
60 | @AfterEach
61 | void stopProxy() {
62 | proxy.stop();
63 | mockServer.stop();
64 | }
65 |
66 | @Test
67 | void testDirect() {
68 | final HttpResponse response = HttpRequest.get("http://localhost:1080/get_books").send();
69 | assertEquals(200, response.statusCode());
70 | assertTrue(response.bodyRaw().contains("Tatum"));
71 | proxy.verify(request().withPath("/get_books"), exactly(0));
72 | }
73 |
74 | @Test
75 | @EnabledOnOs({OS.MAC})
76 | void testDirectHttps() {
77 | final HttpResponse response = HttpRequest.get("https://localhost:1080/get_books").trustAllCerts(true).send();
78 | assertEquals(200, response.statusCode());
79 | assertTrue(response.bodyRaw().contains("Tatum"));
80 | proxy.verify(request().withPath("/get_books"), exactly(0));
81 | }
82 |
83 | @Test
84 | @Disabled
85 | void testHttpProxy() {
86 | final SocketHttpConnectionProvider s = new SocketHttpConnectionProvider();
87 | s.useProxy(ProxyInfo.httpProxy("localhost", 1090, null, null));
88 |
89 | final HttpResponse response = HttpRequest.get("http://localhost:1080/get_books")
90 | .withConnectionProvider(s)
91 | .send();
92 | assertEquals(200, response.statusCode());
93 | assertTrue(response.bodyRaw().contains("Tatum"));
94 | }
95 |
96 | @Test
97 | void testSocks5Proxy() {
98 | final SocketHttpConnectionProvider s = new SocketHttpConnectionProvider();
99 | s.useProxy(ProxyInfo.socks5Proxy("localhost", 1090, null, null));
100 |
101 | final HttpResponse response = HttpRequest.get("http://localhost:1080/get_books")
102 | .withConnectionProvider(s)
103 | .send();
104 | assertEquals(200, response.statusCode());
105 | assertTrue(response.bodyRaw().contains("Tatum"));
106 | proxy.verify(request().withPath("/get_books"), exactly(1));
107 | }
108 |
109 | @Test
110 | @EnabledOnOs({OS.MAC})
111 | void testSocks5ProxyWithHttps() {
112 | final SocketHttpConnectionProvider s = new SocketHttpConnectionProvider();
113 | s.useProxy(ProxyInfo.socks5Proxy("localhost", 1090, null, null));
114 |
115 | final HttpResponse response = HttpRequest.get("https://localhost:1080/get_books")
116 | .withConnectionProvider(s)
117 | .trustAllCerts(true)
118 | .send();
119 | assertEquals(200, response.statusCode());
120 | assertTrue(response.bodyRaw().contains("Tatum"));
121 | proxy.verify(request().withPath("/get_books"), exactly(1));
122 | }
123 |
124 | private void setupMockServer() {
125 | mockServer
126 | .when(
127 | request()
128 | .withPath("/get_books")
129 | )
130 | .respond(
131 | response()
132 | .withHeaders(
133 | new Header(HttpHeaders.Names.CONTENT_TYPE,"application/json")
134 | )
135 | .withBody("" +
136 | "[\n" +
137 | " {\n" +
138 | " \"id\": \"1\",\n" +
139 | " \"title\": \"Xenophon's imperial fiction : on the education of Cyrus\",\n" +
140 | " \"author\": \"James Tatum\",\n" +
141 | " \"isbn\": \"0691067570\",\n" +
142 | " \"publicationDate\": \"1989\"\n" +
143 | " },\n" +
144 | " {\n" +
145 | " \"id\": \"2\",\n" +
146 | " \"title\": \"You are here : personal geographies and other maps of the imagination\",\n" +
147 | " \"author\": \"Katharine A. Harmon\",\n" +
148 | " \"isbn\": \"1568984308\",\n" +
149 | " \"publicationDate\": \"2004\"\n" +
150 | " },\n" +
151 | " {\n" +
152 | " \"id\": \"3\",\n" +
153 | " \"title\": \"You just don't understand : women and men in conversation\",\n" +
154 | " \"author\": \"Deborah Tannen\",\n" +
155 | " \"isbn\": \"0345372050\",\n" +
156 | " \"publicationDate\": \"1990\"\n" +
157 | " }" +
158 | "]")
159 | );
160 | }
161 | }
162 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/RawTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.io.FileUtil;
29 | import jodd.util.StringUtil;
30 | import org.junit.jupiter.api.Test;
31 |
32 | import java.io.ByteArrayInputStream;
33 | import java.io.IOException;
34 | import java.net.URL;
35 |
36 | import static org.junit.jupiter.api.Assertions.assertEquals;
37 | import static org.junit.jupiter.api.Assertions.assertFalse;
38 | import static org.junit.jupiter.api.Assertions.assertNotNull;
39 | import static org.junit.jupiter.api.Assertions.assertTrue;
40 |
41 | class RawTest {
42 |
43 | @Test
44 | void testRawResponse1() throws IOException {
45 | final URL data = RawTest.class.getResource("1-response.txt");
46 |
47 | String fileContent = FileUtil.readString(data.getFile());
48 |
49 | fileContent = StringUtil.replace(fileContent, "\r\n", "\n");
50 |
51 | final HttpResponse response = HttpResponse.readFrom(new ByteArrayInputStream(fileContent.getBytes("UTF-8")));
52 |
53 | final HttpMultiMap headers = response.headers;
54 | assertEquals(7, headers.size());
55 |
56 | assertEquals("no-cache", headers.get("pragma"));
57 | assertEquals("Sat, 23 Mar 2013 23:34:18 GMT", headers.get("date"));
58 | assertEquals("max-age=0, must-revalidate, no-cache, no-store, private, post-check=0, pre-check=0",
59 | headers.get("cache-control"));
60 | assertEquals("no-cache", headers.get("pragma"));
61 | assertEquals("Thu, 01 Jan 1970 00:00:00 GMT", headers.get("expires"));
62 | assertEquals("text/html;charset=UTF-8", headers.get("content-type"));
63 | assertEquals("close", headers.get("connection"));
64 | assertEquals("102", headers.get("content-length"));
65 |
66 | assertEquals("no-cache", response.header("Pragma"));
67 | assertEquals("text/html;charset=UTF-8" , response.contentType());
68 | assertEquals("text/html" , response.mediaType());
69 | assertEquals("UTF-8" , response.charset());
70 |
71 | assertNotNull(response.contentLength());
72 |
73 | final String rawBody = response.bodyRaw();
74 | final String textBody = response.bodyText();
75 |
76 | assertTrue(rawBody.startsWith(""));
77 | assertTrue(rawBody.endsWith(""));
78 |
79 | assertTrue(rawBody.contains("This is UTF8 Encoding."));
80 | assertFalse(rawBody.contains("Тхис ис УТФ8 Енцодинг."));
81 | assertTrue(textBody.contains("Тхис ис УТФ8 Енцодинг."));
82 |
83 | assertEquals(77, textBody.length());
84 |
85 | final int len = textBody.getBytes("UTF-8").length;
86 |
87 | assertEquals(94, rawBody.length());
88 | assertEquals(len, rawBody.length());
89 | }
90 |
91 | @Test
92 | void testRawResponse4() throws IOException {
93 | final URL data = RawTest.class.getResource("4-response.txt");
94 |
95 | String fileContent = FileUtil.readString(data.getFile());
96 |
97 | fileContent = StringUtil.replace(fileContent, "\n", "\r\n");
98 | fileContent = StringUtil.replace(fileContent, "\r\r\n", "\r\n");
99 |
100 | final HttpResponse response = HttpResponse.readFrom(new ByteArrayInputStream(fileContent.getBytes("UTF-8")));
101 |
102 | final String body = response.bodyText();
103 |
104 | assertEquals(
105 | "Wikipedia in\n" +
106 | "\n" +
107 | "chunks.", body.replace("\r\n", "\n"));
108 | }
109 |
110 |
111 | @Test
112 | void testRawResponse5() throws IOException {
113 | final URL data = RawTest.class.getResource("5-response.txt");
114 |
115 | String fileContent = FileUtil.readString(data.getFile());
116 |
117 | fileContent = StringUtil.replace(fileContent, "\n", "\r\n");
118 | fileContent = StringUtil.replace(fileContent, "\r\r\n", "\r\n");
119 |
120 | final HttpResponse response = HttpResponse.readFrom(new ByteArrayInputStream(fileContent.getBytes("UTF-8")));
121 |
122 | final String body = response.bodyText();
123 |
124 | assertEquals(
125 | "Wikipedia in\n" +
126 | "\n" +
127 | "chunks.", body.replace("\r\n", "\n"));
128 |
129 | assertEquals("TheData", response.header("SomeAfterHeader"));
130 | }
131 |
132 | @Test
133 | void testRawResponse6() throws IOException {
134 | final URL data = RawTest.class.getResource("6-response.txt");
135 |
136 | String fileContent = FileUtil.readString(data.getFile());
137 |
138 | fileContent = StringUtil.replace(fileContent, "\n", "\r\n");
139 | fileContent = StringUtil.replace(fileContent, "\r\r\n", "\r\n");
140 |
141 | final HttpResponse response = HttpResponse.readFrom(new ByteArrayInputStream(fileContent.getBytes("UTF-8")));
142 |
143 | assertEquals(200, response.statusCode());
144 | assertEquals("", response.statusPhrase);
145 |
146 | final String body = response.bodyText();
147 |
148 | assertEquals(
149 | "Wikipedia in\n" +
150 | "\n" +
151 | "chunks.", body.replace("\r\n", "\n"));
152 |
153 | assertEquals("TheData", response.header("SomeAfterHeader"));
154 | }
155 |
156 |
157 | }
158 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/RemoveHeaderTest.java:
--------------------------------------------------------------------------------
1 | package jodd.http;
2 |
3 | import org.junit.jupiter.api.Test;
4 |
5 | import java.io.ByteArrayOutputStream;
6 | import java.io.IOException;
7 |
8 | import static org.junit.jupiter.api.Assertions.assertFalse;
9 | import static org.junit.jupiter.api.Assertions.assertNotNull;
10 | import static org.junit.jupiter.api.Assertions.assertNull;
11 |
12 | class RemoveHeaderTest {
13 |
14 | @Test
15 | void testRemoveHeader() {
16 | HttpRequest request = HttpRequest
17 | .get("https://example.com")
18 | .header("x-dummy-header", "remove me");
19 |
20 | assertNotNull(request.header("x-dummy-header"));
21 |
22 | request.headerRemove("x-dummy-header");
23 |
24 | assertNull(request.header("x-dummy-header"));
25 | }
26 |
27 | @Test
28 | void testRemoveHeaderUserAgent() throws IOException {
29 | HttpBase.Defaults.headers.remove("User-Agent");
30 |
31 | HttpRequest request = HttpRequest
32 | .get("https://example.com")
33 | .header("x-dummy-header", "remove me");
34 |
35 | assertNull(request.header("User-Agent"));
36 |
37 | request.headerRemove("User-Agent");
38 |
39 | assertNull(request.header("User-Agent"));
40 |
41 | ByteArrayOutputStream baos = new ByteArrayOutputStream();
42 | request.sendTo(baos);
43 | String out = baos.toString();
44 |
45 | assertFalse(out.contains("User-Agent"));
46 |
47 | HttpBase.Defaults.headers.addHeader("User-Agent", "Jodd HTTP");
48 | }
49 | }
50 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/TestServer.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import jodd.io.FileUtil;
29 |
30 | import java.io.File;
31 | import java.net.URL;
32 |
33 |
34 | /**
35 | * Common server content.
36 | */
37 | public abstract class TestServer {
38 |
39 | protected File webRoot;
40 |
41 | public void start() throws Exception {
42 | webRoot = FileUtil.createTempDirectory("jodd-http", "test");
43 | webRoot.deleteOnExit();
44 |
45 | // web-inf
46 |
47 | File webInfFolder = new File(webRoot, "WEB-INF");
48 | webInfFolder.mkdir();
49 |
50 | // web.xml
51 |
52 | URL webXmlUrl = TestServer.class.getResource("web.xml");
53 | File webXmlFile = FileUtil.toFile(webXmlUrl);
54 |
55 | FileUtil.copy(webXmlFile, webInfFolder);
56 |
57 | // lib folder
58 |
59 | File libFolder = new File(webInfFolder, "lib");
60 | libFolder.mkdir();
61 |
62 | // classes
63 |
64 | File classes = new File(webInfFolder, "classes/jodd/http/fixture");
65 | classes.mkdirs();
66 |
67 | URL echoServletUrl = TestServer.class.getResource("fixture/EchoServlet.class");
68 | File echoServletFile = FileUtil.toFile(echoServletUrl);
69 | FileUtil.copyFileToDir(echoServletFile, classes);
70 |
71 | echoServletUrl = TestServer.class.getResource("fixture/Echo2Servlet.class");
72 | echoServletFile = FileUtil.toFile(echoServletUrl);
73 | FileUtil.copyFileToDir(echoServletFile, classes);
74 |
75 | echoServletUrl = TestServer.class.getResource("fixture/Echo3Servlet.class");
76 | echoServletFile = FileUtil.toFile(echoServletUrl);
77 | FileUtil.copyFileToDir(echoServletFile, classes);
78 |
79 | URL redirectServletUrl = TestServer.class.getResource("fixture/RedirectServlet.class");
80 | File redirectServletFile = FileUtil.toFile(redirectServletUrl);
81 | FileUtil.copyFileToDir(redirectServletFile, classes);
82 |
83 | URL targetServletUrl = TestServer.class.getResource("fixture/TargetServlet.class");
84 | File targetServletFile = FileUtil.toFile(targetServletUrl);
85 | FileUtil.copyFileToDir(targetServletFile, classes);
86 | }
87 |
88 | public void stop() throws Exception {
89 | webRoot.delete();
90 | }
91 | }
--------------------------------------------------------------------------------
/src/test/java/jodd/http/TimeoutTest.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.junit.jupiter.api.AfterAll;
29 | import org.junit.jupiter.api.BeforeAll;
30 | import org.junit.jupiter.api.Test;
31 |
32 | import static org.junit.jupiter.api.Assertions.assertEquals;
33 | import static org.junit.jupiter.api.Assertions.fail;
34 |
35 | class TimeoutTest {
36 |
37 | static TestServer testServer;
38 |
39 | @BeforeAll
40 | static void startServer() throws Exception {
41 | testServer = new TomcatServer();
42 | testServer.start();
43 | }
44 |
45 | @AfterAll
46 | static void stopServer() throws Exception {
47 | testServer.stop();
48 | }
49 |
50 | @Test
51 | void testTimeout() {
52 | HttpRequest httpRequest = HttpRequest.get("localhost:8173/slow");
53 | httpRequest.timeout(1000);
54 |
55 | try {
56 | httpRequest.send();
57 | fail("error");
58 | }
59 | catch(HttpException ignore) {
60 | }
61 |
62 | httpRequest = HttpRequest.get("localhost:8173/slow");
63 | httpRequest.timeout(6000);
64 |
65 | int status = httpRequest.send().statusCode();
66 |
67 | assertEquals(200, status);
68 | }
69 | }
70 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/TomcatServer.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http;
27 |
28 | import org.apache.catalina.startup.Tomcat;
29 |
30 | /**
31 | * Tomcat Server.
32 | */
33 | public class TomcatServer extends TestServer {
34 |
35 | protected Tomcat tomcat;
36 |
37 | @Override
38 | public void start() throws Exception {
39 | super.start();
40 |
41 | String workingDir = System.getProperty("java.io.tmpdir");
42 |
43 | tomcat = new Tomcat();
44 | tomcat.setPort(8173);
45 | tomcat.setBaseDir(workingDir);
46 | tomcat.addWebapp("", webRoot.getAbsolutePath());
47 |
48 | tomcat.start();
49 | }
50 |
51 | @Override
52 | public void stop() throws Exception {
53 | tomcat.stop();
54 | tomcat.destroy();
55 | super.stop();
56 | }
57 | }
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/Data.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.fixture;
27 |
28 | import javax.servlet.http.Cookie;
29 | import java.util.Map;
30 |
31 | public class Data {
32 |
33 | public static Data ref;
34 |
35 | public boolean get;
36 | public boolean post;
37 | public String queryString;
38 | public String body;
39 | public Map header;
40 | public Map params;
41 | public Map parts;
42 | public Map fileNames;
43 | public Cookie[] cookies;
44 | }
45 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/Echo2Servlet.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.fixture;
27 |
28 | import javax.servlet.annotation.MultipartConfig;
29 | import javax.servlet.http.HttpServletRequest;
30 | import java.io.IOException;
31 | import java.nio.charset.StandardCharsets;
32 |
33 | @MultipartConfig
34 | public class Echo2Servlet extends EchoServlet {
35 |
36 | @Override
37 | protected void readAll(final HttpServletRequest req) throws IOException {
38 | Data.ref.queryString = req.getQueryString();
39 | Data.ref.header = copyHeaders(req);
40 | Data.ref.params = copyParams(req, StandardCharsets.UTF_8.name());
41 | Data.ref.parts = copyParts(req);
42 | Data.ref.fileNames = copyFileName(req);
43 | }
44 |
45 | }
46 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/Echo3Servlet.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.fixture;
27 |
28 | import javax.servlet.annotation.MultipartConfig;
29 | import javax.servlet.http.HttpServletRequest;
30 | import java.nio.charset.StandardCharsets;
31 |
32 | @MultipartConfig
33 | public class Echo3Servlet extends EchoServlet {
34 |
35 | @Override
36 | protected void readAll(final HttpServletRequest req) {
37 | Data.ref.queryString = req.getQueryString();
38 | Data.ref.header = copyHeaders(req);
39 | Data.ref.params = copyParams(req, StandardCharsets.ISO_8859_1.name());
40 | Data.ref.parts = copyParts(req);
41 | Data.ref.fileNames = copyFileName(req);
42 | }
43 |
44 | }
45 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/EchoServlet.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.fixture;
27 |
28 | import jodd.io.IOUtil;
29 | import jodd.util.StringUtil;
30 | import org.apache.catalina.core.ApplicationPart;
31 |
32 | import javax.servlet.ServletException;
33 | import javax.servlet.http.Cookie;
34 | import javax.servlet.http.HttpServlet;
35 | import javax.servlet.http.HttpServletRequest;
36 | import javax.servlet.http.HttpServletResponse;
37 | import javax.servlet.http.Part;
38 | import java.io.BufferedReader;
39 | import java.io.IOException;
40 | import java.io.StringWriter;
41 | import java.nio.charset.Charset;
42 | import java.nio.charset.StandardCharsets;
43 | import java.util.Collection;
44 | import java.util.Enumeration;
45 | import java.util.HashMap;
46 | import java.util.Map;
47 |
48 | public class EchoServlet extends HttpServlet {
49 |
50 | @Override
51 | protected void doGet(final HttpServletRequest req, final HttpServletResponse resp) throws ServletException, IOException {
52 | Data.ref = new Data();
53 | Data.ref.get = true;
54 | Data.ref.post = false;
55 | readAll(req);
56 |
57 | if (Data.ref.cookies != null) {
58 | for (final Cookie cookie : Data.ref.cookies) {
59 | cookie.setValue(cookie.getValue() + "!");
60 | resp.addCookie(cookie);
61 | }
62 | }
63 |
64 | write(resp, Data.ref.body);
65 | }
66 |
67 | @Override
68 | protected void doPost(final HttpServletRequest req, final HttpServletResponse resp) throws ServletException, IOException {
69 | Data.ref = new Data();
70 | Data.ref.post = true;
71 | Data.ref.get = false;
72 | readAll(req);
73 | write(resp, Data.ref.body);
74 | }
75 |
76 | // ---------------------------------------------------------------- write
77 |
78 | protected void write(final HttpServletResponse resp, final String text) throws IOException {
79 | if (text != null) {
80 | resp.setContentLength(text.getBytes(StandardCharsets.UTF_8).length);
81 | resp.setContentType("text/html;charset=UTF-8");
82 | resp.getWriter().write(text);
83 | resp.flushBuffer();
84 | }
85 | }
86 |
87 | // ---------------------------------------------------------------- read all
88 |
89 | protected void readAll(final HttpServletRequest req) throws IOException {
90 | Data.ref.body = readRequestBody(req);
91 | Data.ref.queryString = req.getQueryString();
92 | Data.ref.header = copyHeaders(req);
93 | Data.ref.cookies = req.getCookies();
94 | }
95 |
96 | protected String readRequestBody(final HttpServletRequest request) throws IOException {
97 | final BufferedReader buff = request.getReader();
98 | final StringWriter out = new StringWriter();
99 | IOUtil.copy(buff, out);
100 | return out.toString();
101 | }
102 |
103 | protected Map copyHeaders(final HttpServletRequest req) {
104 | final Enumeration enumeration = req.getHeaderNames();
105 | final Map header = new HashMap<>();
106 |
107 | while (enumeration.hasMoreElements()) {
108 | final String name = enumeration.nextElement().toString();
109 | final String value = req.getHeader(name);
110 | header.put(name, value);
111 | }
112 |
113 | return header;
114 | }
115 |
116 | protected Map copyParams(final HttpServletRequest req, final String fromEncoding) {
117 | final String charset = req.getParameter("enc");
118 |
119 | final Enumeration enumeration = req.getParameterNames();
120 | final Map params = new HashMap<>();
121 |
122 | while (enumeration.hasMoreElements()) {
123 | final String name = enumeration.nextElement().toString();
124 | String value = req.getParameter(name);
125 | if (charset != null) {
126 | value = StringUtil.convertCharset(value, Charset.forName(fromEncoding), Charset.forName(charset));
127 | }
128 | params.put(name, value);
129 | }
130 |
131 | return params;
132 | }
133 |
134 | protected Map copyParts(final HttpServletRequest req) {
135 | final Map parts = new HashMap<>();
136 | if (req.getContentType() == null) {
137 | return parts;
138 | }
139 | if (req.getContentType() != null && !req.getContentType().toLowerCase().contains("multipart/form-data")) {
140 | return parts;
141 | }
142 |
143 | final String enc = "UTF-8";
144 |
145 | try {
146 | final Collection prs = req.getParts();
147 |
148 | for (final Part p : prs) {
149 | parts.put(p.getName(), new String(IOUtil.readBytes(p.getInputStream()), enc));
150 | }
151 | }
152 | catch (final IOException | ServletException e) {
153 | e.printStackTrace();
154 | }
155 |
156 | return parts;
157 | }
158 |
159 | protected Map copyFileName(final HttpServletRequest req) {
160 | final Map parts = new HashMap<>();
161 | if (req.getContentType() == null) {
162 | return parts;
163 | }
164 | if (req.getContentType() != null && !req.getContentType().toLowerCase().contains("multipart/form-data")) {
165 | return parts;
166 | }
167 |
168 | try {
169 | final Collection prs = req.getParts();
170 |
171 | for (final Part p : prs) {
172 | if (p instanceof ApplicationPart) {
173 | final ApplicationPart ap = (ApplicationPart) p;
174 | parts.put(p.getName(), ap.getSubmittedFileName());
175 | }
176 | }
177 | }
178 | catch (final IOException | ServletException e) {
179 | e.printStackTrace();
180 | }
181 |
182 | return parts;
183 | }
184 |
185 | }
186 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/RedirectServlet.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.fixture;
27 |
28 | import javax.servlet.ServletException;
29 | import javax.servlet.http.HttpServlet;
30 | import javax.servlet.http.HttpServletRequest;
31 | import javax.servlet.http.HttpServletResponse;
32 | import java.io.IOException;
33 |
34 | /**
35 | * Simply redirects to '/target'.
36 | */
37 | public class RedirectServlet extends HttpServlet {
38 |
39 | @Override
40 | protected void doGet(HttpServletRequest req, HttpServletResponse resp)
41 | throws ServletException, IOException {
42 |
43 | resp.sendRedirect("/target");
44 | }
45 | }
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/SlowServlet.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.fixture;
27 |
28 | import jodd.util.ThreadUtil;
29 |
30 | import javax.servlet.ServletException;
31 | import javax.servlet.http.HttpServlet;
32 | import javax.servlet.http.HttpServletRequest;
33 | import javax.servlet.http.HttpServletResponse;
34 | import java.io.IOException;
35 | import java.nio.charset.StandardCharsets;
36 |
37 | public class SlowServlet extends HttpServlet {
38 |
39 | @Override
40 | protected void doGet(final HttpServletRequest req, final HttpServletResponse resp) throws ServletException, IOException {
41 | ThreadUtil.sleep(5000);
42 | write(resp, "OK");
43 | }
44 |
45 | protected void write(final HttpServletResponse resp, final String text) throws IOException {
46 | if (text != null) {
47 | resp.setContentLength(text.getBytes(StandardCharsets.UTF_8.name()).length);
48 | resp.setContentType("text/html;charset=UTF-8");
49 | resp.getWriter().write(text);
50 | resp.flushBuffer();
51 | }
52 | }
53 |
54 | }
55 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/StringHttpRequest.java:
--------------------------------------------------------------------------------
1 | package jodd.http.fixture;
2 |
3 | import jodd.http.HttpConnection;
4 | import jodd.http.HttpConnectionProvider;
5 | import jodd.http.HttpRequest;
6 | import jodd.http.ProxyInfo;
7 |
8 | import java.io.ByteArrayInputStream;
9 | import java.io.ByteArrayOutputStream;
10 | import java.io.InputStream;
11 | import java.io.OutputStream;
12 |
13 | public class StringHttpRequest {
14 |
15 | public static HttpRequest create(final String payload) {
16 | return new HttpRequest().withConnectionProvider(new HttpConnectionProvider() {
17 | @Override
18 | public void useProxy(ProxyInfo proxyInfo) {
19 | }
20 |
21 | @Override
22 | public HttpConnection createHttpConnection(HttpRequest httpRequest) {
23 | return new HttpConnection() {
24 |
25 | private final ByteArrayInputStream in = new ByteArrayInputStream(payload.getBytes());
26 | private final ByteArrayOutputStream out = new ByteArrayOutputStream(1024);
27 |
28 | @Override
29 | public void init() {
30 | }
31 |
32 | @Override
33 | public OutputStream getOutputStream() {
34 | return out;
35 | }
36 |
37 | @Override
38 | public InputStream getInputStream() {
39 | return in;
40 | }
41 |
42 | @Override
43 | public void close() {
44 | }
45 |
46 | @Override
47 | public void setTimeout(int milliseconds) {
48 | }
49 | };
50 | }
51 | });
52 | }
53 | }
54 |
--------------------------------------------------------------------------------
/src/test/java/jodd/http/fixture/TargetServlet.java:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2003-present, Jodd Team (http://jodd.org)
2 | // All rights reserved.
3 | //
4 | // Redistribution and use in source and binary forms, with or without
5 | // modification, are permitted provided that the following conditions are met:
6 | //
7 | // 1. Redistributions of source code must retain the above copyright notice,
8 | // this list of conditions and the following disclaimer.
9 | //
10 | // 2. Redistributions in binary form must reproduce the above copyright
11 | // notice, this list of conditions and the following disclaimer in the
12 | // documentation and/or other materials provided with the distribution.
13 | //
14 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 | // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18 | // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 | // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 | // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 | // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 | // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 | // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 | // POSSIBILITY OF SUCH DAMAGE.
25 |
26 | package jodd.http.fixture;
27 |
28 | import javax.servlet.ServletException;
29 | import javax.servlet.http.HttpServlet;
30 | import javax.servlet.http.HttpServletRequest;
31 | import javax.servlet.http.HttpServletResponse;
32 | import java.io.IOException;
33 |
34 | public class TargetServlet extends HttpServlet {
35 |
36 | @Override
37 | protected void doGet(HttpServletRequest req, HttpServletResponse resp)
38 | throws ServletException, IOException {
39 |
40 | resp.getWriter().write("target!");
41 | }
42 |
43 |
44 | }
--------------------------------------------------------------------------------
/src/test/resources/jodd/http/1-response.txt:
--------------------------------------------------------------------------------
1 | HTTP/1.1 200 OK
2 | Date: Sat, 23 Mar 2013 23:34:18 GMT
3 | Cache-Control: max-age=0, must-revalidate, no-cache, no-store, private, post-check=0, pre-check=0
4 | Pragma: no-cache
5 | Expires: Thu, 01 Jan 1970 00:00:00 GMT
6 | Content-Type: text/html;charset=UTF-8
7 | Connection: close
8 | Content-Length: 102
9 |
10 |
11 |
12 |
13 | This is UTF8 Encoding.
14 | Тхис ис УТФ8 Енцодинг.
15 |
16 |
17 |
--------------------------------------------------------------------------------
/src/test/resources/jodd/http/2-response.txt:
--------------------------------------------------------------------------------
1 | HTTP/1.1 200 OK
2 | Content-Type: application/json; charset=UTF-8
3 | Date: Thu, 27 Feb 2014 21:10:55 GMT
4 | Expires: Fri, 28 Feb 2014 21:10:55 GMT
5 | Cache-Control: public, max-age=86400
6 | Vary: Accept-Language
7 | Access-Control-Allow-Origin: *
8 | Server: mafe
9 | X-Xss-Protection: 1; mode=block
10 | X-Frame-Options: SAMEORIGIN
11 | Alternate-Protocol: 80:quic
12 | Connection: close
--------------------------------------------------------------------------------
/src/test/resources/jodd/http/3-response.txt:
--------------------------------------------------------------------------------
1 | HTTP/1.1 200 OK
2 | Content-Type: application/json; charset=UTF-8
3 | Date: Thu, 27 Feb 2014 21:10:55 GMT
4 | Expires: Fri, 28 Feb 2014 21:10:55 GMT
5 | Cache-Control: public, max-age=86400
6 | Vary: Accept-Language
7 | Access-Control-Allow-Origin: *
8 | Server: mafe
9 | X-Xss-Protection: 1; mode=block
10 | X-Frame-Options: SAMEORIGIN
11 | Alternate-Protocol: 80:quic
12 | Connection: close
13 |
14 | Body!
--------------------------------------------------------------------------------
/src/test/resources/jodd/http/4-response.txt:
--------------------------------------------------------------------------------
1 | HTTP/1.1 200 OK
2 | content-type:text/html; charset=utf-8
3 | Transfer-Encoding: chunked
4 | Connection: close
5 |
6 | 4
7 | Wiki
8 | 5
9 | pedia
10 | e
11 | in
12 |
13 | chunks.
14 | 0
15 |
--------------------------------------------------------------------------------
/src/test/resources/jodd/http/5-response.txt:
--------------------------------------------------------------------------------
1 | HTTP/1.1 200 OK
2 | content-type:text/html; charset=utf-8
3 | Transfer-Encoding: chunked
4 | Connection: close
5 |
6 | 4
7 | Wiki
8 | 5
9 | pedia
10 | e
11 | in
12 |
13 | chunks.
14 | 0
15 | SomeAfterHeader: TheData
16 |
--------------------------------------------------------------------------------
/src/test/resources/jodd/http/6-response.txt:
--------------------------------------------------------------------------------
1 | HTTP/1.1 200
2 | content-type:text/html; charset=utf-8
3 | Content-Length: 102
4 | Transfer-Encoding: chunked
5 | Connection: close
6 |
7 | 4
8 | Wiki
9 | 5
10 | pedia
11 | e
12 | in
13 |
14 | chunks.
15 | 0
16 | SomeAfterHeader: TheData
17 |
--------------------------------------------------------------------------------
/src/test/resources/jodd/http/web.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
6 |
7 |
8 | EchoServlet
9 | EchoServlet
10 | jodd.http.fixture.EchoServlet
11 |
12 |
13 |
14 | EchoServlet
15 | /echo
16 |
17 |
18 |
19 | Echo2Servlet
20 | Echo2Servlet
21 | jodd.http.fixture.Echo2Servlet
22 |
23 |
24 |
25 | Echo2Servlet
26 | /echo2
27 |
28 |
29 |
30 | Echo3Servlet
31 | Echo3Servlet
32 | jodd.http.fixture.Echo3Servlet
33 |
34 |
35 |
36 | Echo3Servlet
37 | /echo3
38 |
39 |
40 |
41 | TargetServlet
42 | TargetServlet
43 | jodd.http.fixture.TargetServlet
44 |
45 |
46 |
47 | TargetServlet
48 | /target
49 |
50 |
51 |
52 | RedirectServlet
53 | RedirectServlet
54 | jodd.http.fixture.RedirectServlet
55 |
56 |
57 |
58 | RedirectServlet
59 | /redirect
60 |
61 |
62 |
63 | SlowServlet
64 | SlowServlet
65 | jodd.http.fixture.SlowServlet
66 |
67 |
68 |
69 | SlowServlet
70 | /slow
71 |
72 |
73 |
--------------------------------------------------------------------------------