1515 */
1616package org .asynchttpclient .uri ;
1717
18+ import org .jetbrains .annotations .Nullable ;
19+
1820import static org .asynchttpclient .util .Assertions .assertNotNull ;
1921import static org .asynchttpclient .util .MiscUtils .isNonEmpty ;
2022
2123final class UriParser {
2224
23- public String scheme ;
24- public String host ;
25+ public @ Nullable String scheme ;
26+ public @ Nullable String host ;
2527 public int port = -1 ;
26- public String query ;
27- public String fragment ;
28- private String authority ;
29- public String path ;
30- public String userInfo ;
28+ public @ Nullable String query ;
29+ public @ Nullable String fragment ;
30+ private @ Nullable String authority ;
31+ public String path = "" ;
32+ public @ Nullable String userInfo ;
3133
32- private String originalUrl ;
34+ private final String originalUrl ;
3335 private int start , end , currentIndex ;
3436
37+ private UriParser (final String originalUrl ) {
38+ this .originalUrl = originalUrl ;
39+ }
40+
3541 private void trimLeft () {
3642 while (start < end && originalUrl .charAt (start ) <= ' ' ) {
3743 start ++;
@@ -86,7 +92,7 @@ private void computeInitialScheme() {
8692 }
8793 }
8894
89- private boolean overrideWithContext (Uri context ) {
95+ private boolean overrideWithContext (@ Nullable Uri context ) {
9096
9197 boolean isRelative = false ;
9298
@@ -126,7 +132,9 @@ private void trimFragment() {
126132 }
127133 }
128134
129- private void inheritContextQuery (Uri context , boolean isRelative ) {
135+ // isRelative can be true only when context is not null
136+ @ SuppressWarnings ("NullAway" )
137+ private void inheritContextQuery (@ Nullable Uri context , boolean isRelative ) {
130138 // see RFC2396 5.2.2: query and fragment inheritance
131139 if (isRelative && currentIndex == end ) {
132140 query = context .getQuery ();
@@ -156,7 +164,7 @@ private boolean currentPositionStartsWith2Slashes() {
156164 return originalUrl .regionMatches (currentIndex , "//" , 0 , 2 );
157165 }
158166
159- private void computeAuthority () {
167+ private String computeAuthority () {
160168 int authorityEndPosition = findWithinCurrentRange ('/' );
161169 if (authorityEndPosition == -1 ) {
162170 authorityEndPosition = findWithinCurrentRange ('?' );
@@ -166,59 +174,60 @@ private void computeAuthority() {
166174 }
167175 host = authority = originalUrl .substring (currentIndex , authorityEndPosition );
168176 currentIndex = authorityEndPosition ;
177+ return authority ;
169178 }
170179
171- private void computeUserInfo () {
172- int atPosition = authority .indexOf ('@' );
180+ private void computeUserInfo (String nonNullAuthority ) {
181+ int atPosition = nonNullAuthority .indexOf ('@' );
173182 if (atPosition != -1 ) {
174- userInfo = authority .substring (0 , atPosition );
175- host = authority .substring (atPosition + 1 );
183+ userInfo = nonNullAuthority .substring (0 , atPosition );
184+ host = nonNullAuthority .substring (atPosition + 1 );
176185 } else {
177186 userInfo = null ;
178187 }
179188 }
180189
181- private boolean isMaybeIPV6 () {
190+ private boolean isMaybeIPV6 (String nonNullHost ) {
182191 // If the host is surrounded by [ and ] then its an IPv6
183192 // literal address as specified in RFC2732
184- return host .length () > 0 && host .charAt (0 ) == '[' ;
193+ return nonNullHost .length () > 0 && nonNullHost .charAt (0 ) == '[' ;
185194 }
186195
187- private void computeIPV6 () {
188- int positionAfterClosingSquareBrace = host .indexOf (']' ) + 1 ;
196+ private void computeIPV6 (String nonNullHost ) {
197+ int positionAfterClosingSquareBrace = nonNullHost .indexOf (']' ) + 1 ;
189198 if (positionAfterClosingSquareBrace > 1 ) {
190199
191200 port = -1 ;
192201
193- if (host .length () > positionAfterClosingSquareBrace ) {
194- if (host .charAt (positionAfterClosingSquareBrace ) == ':' ) {
202+ if (nonNullHost .length () > positionAfterClosingSquareBrace ) {
203+ if (nonNullHost .charAt (positionAfterClosingSquareBrace ) == ':' ) {
195204 // see RFC2396: port can be null
196205 int portPosition = positionAfterClosingSquareBrace + 1 ;
197- if (host .length () > portPosition ) {
198- port = Integer .parseInt (host .substring (portPosition ));
206+ if (nonNullHost .length () > portPosition ) {
207+ port = Integer .parseInt (nonNullHost .substring (portPosition ));
199208 }
200209 } else {
201210 throw new IllegalArgumentException ("Invalid authority field: " + authority );
202211 }
203212 }
204213
205- host = host .substring (0 , positionAfterClosingSquareBrace );
214+ host = nonNullHost .substring (0 , positionAfterClosingSquareBrace );
206215
207216 } else {
208217 throw new IllegalArgumentException ("Invalid authority field: " + authority );
209218 }
210219 }
211220
212- private void computeRegularHostPort () {
213- int colonPosition = host .indexOf (':' );
221+ private void computeRegularHostPort (String nonNullHost ) {
222+ int colonPosition = nonNullHost .indexOf (':' );
214223 port = -1 ;
215224 if (colonPosition >= 0 ) {
216225 // see RFC2396: port can be null
217226 int portPosition = colonPosition + 1 ;
218- if (host .length () > portPosition ) {
219- port = Integer .parseInt (host .substring (portPosition ));
227+ if (nonNullHost .length () > portPosition ) {
228+ port = Integer .parseInt (nonNullHost .substring (portPosition ));
220229 }
221- host = host .substring (0 , colonPosition );
230+ host = nonNullHost .substring (0 , colonPosition );
222231 }
223232 }
224233
@@ -293,14 +302,15 @@ private void parseAuthority() {
293302 if (!currentPositionStartsWith4Slashes () && currentPositionStartsWith2Slashes ()) {
294303 currentIndex += 2 ;
295304
296- computeAuthority ();
297- computeUserInfo ();
305+ String nonNullAuthority = computeAuthority ();
306+ computeUserInfo (nonNullAuthority );
298307
299308 if (host != null ) {
300- if (isMaybeIPV6 ()) {
301- computeIPV6 ();
309+ String nonNullHost = host ;
310+ if (isMaybeIPV6 (nonNullHost )) {
311+ computeIPV6 (nonNullHost );
302312 } else {
303- computeRegularHostPort ();
313+ computeRegularHostPort (nonNullHost );
304314 }
305315 }
306316
@@ -336,17 +346,12 @@ private void computePath(boolean queryOnly) {
336346 // Parse the file path if any
337347 if (currentIndex < end ) {
338348 computeRegularPath ();
339- } else if (queryOnly && path != null ) {
349+ } else if (queryOnly ) {
340350 computeQueryOnlyPath ();
341- } else if (path == null ) {
342- path = "" ;
343351 }
344352 }
345353
346- public void parse (Uri context , final String originalUrl ) {
347-
348- assertNotNull (originalUrl , "originalUrl" );
349- this .originalUrl = originalUrl ;
354+ private void parse (@ Nullable Uri context ) {
350355 end = originalUrl .length ();
351356
352357 trimLeft ();
@@ -362,4 +367,11 @@ public void parse(Uri context, final String originalUrl) {
362367 parseAuthority ();
363368 computePath (queryOnly );
364369 }
370+
371+ public static UriParser parse (@ Nullable Uri context , final String originalUrl ) {
372+ assertNotNull (originalUrl , "originalUrl" );
373+ final UriParser parser = new UriParser (originalUrl );
374+ parser .parse (context );
375+ return parser ;
376+ }
365377}
0 commit comments