Skip to content

Sd-1897-url validation updated#503

Open
palatsangeetha wants to merge 1 commit intodevfrom
SD-1897-restrict-question-mark-sandbox-url-
Open

Sd-1897-url validation updated#503
palatsangeetha wants to merge 1 commit intodevfrom
SD-1897-restrict-question-mark-sandbox-url-

Conversation

@palatsangeetha
Copy link
Copy Markdown
Collaborator

No description provided.

@qodo-code-review
Copy link
Copy Markdown

Review Summary by Qodo

Introduce Url value object with query parameter validation

✨ Enhancement 🐞 Bug fix

Grey Divider

Walkthroughs

Description
• Introduce Url value object for validated URL handling
  - Encapsulates URL validation logic with Jackson serialization support
  - Adds validation to reject URLs containing query parameters (question marks)
• Refactor CounterpartConfiguration to use Url type
  - Replace String url field with Url url for type safety
  - Move validation logic from static method to Url class
• Update all URL usages across codebase
  - Call .getValue() to extract string from Url objects
  - Use Url.ofTrusted() for internally-generated URLs
  - Use Url.validate() for external URL validation
• Improve null/blank checking with isBlank() method
Diagram
flowchart LR
  A["String url field"] -->|"Refactored to"| B["Url value object"]
  B -->|"Encapsulates"| C["URL validation logic"]
  C -->|"Adds check for"| D["Query parameters"]
  B -->|"Provides"| E["getValue method"]
  E -->|"Used in"| F["ConformanceParty & ConformanceOrchestrator"]
Loading

Grey Divider

File Changes

1. core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java ✨ Enhancement +129/-0

New Url value object with validation

• New value object class for validated URLs with immutable design
• Implements Url.of() for validated URL creation and Url.ofTrusted() for deserialization
• Adds query parameter validation to reject URLs containing ?
• Provides getValue(), isBlank(), and length() methods for URL access
• Includes Jackson annotations for JSON serialization/deserialization
• Implements equals(), hashCode(), and toString() for proper object semantics

core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java


2. core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java ✨ Enhancement +2/-29

Replace String url with Url value object

• Change url field type from String to Url
• Remove static validateUrl() method (moved to Url class)
• Remove imports for URI, URISyntaxException, Stream, and UserFacingException
• Add import for new Url class

core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java


3. core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java ✨ Enhancement +3/-3

Update URL field access with getValue method

• Update asyncCounterpartNotification() to call .getValue() on Url object
• Replace isEmpty() check with isBlank() for better null/whitespace handling
• Update _getCounterpartUrl() to call .getValue() when concatenating URL with path

core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java


View more (2)
4. sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceOrchestrator.java ✨ Enhancement +1/-1

Update URL access with getValue method

• Update URL concatenation to call .getValue() on Url object in notifyNextActionParty() method

sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceOrchestrator.java


5. sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java ✨ Enhancement +10/-8

Integrate Url value object in sandbox configuration

• Add import for Url class
• Wrap internally-generated URLs with Url.ofTrusted() in _createSandbox() method
• Update URL field access to call .getValue() in _getSandboxConfig() method
• Update URL validation call from CounterpartConfiguration.validateUrl() to Url.validate() in
 _updateSandboxConfig() method
• Wrap user-provided URL with Url.ofTrusted() after validation
• Update URL field access with .getValue() in orchestrator URL setup

sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java


Grey Divider

Qodo Logo

@qodo-code-review
Copy link
Copy Markdown

qodo-code-review bot commented Apr 9, 2026

Code Review by Qodo

🐞 Bugs (3)   📘 Rule violations (0)   📎 Requirement gaps (0)   🎨 UX Issues (0)
🐞\ ≡ Correctness (2) ☼ Reliability (1)

Grey Divider


Action required

1. Null Url NPE risk 🐞
Description
ConformanceParty._getCounterpartUrl dereferences counterpartConfiguration.getUrl().getValue()
without checking for null, but other code paths treat the URL as nullable, so a missing/omitted URL
can now crash with a NullPointerException. The same dereference pattern exists in sandbox components
when composing notification/config URLs.
Code

core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java[302]

+    var url = counterpartConfiguration.getUrl().getValue() + path;
Evidence
CounterpartConfiguration.url has no default and is therefore nullable; ConformanceParty explicitly
guards for null in asyncCounterpartNotification, proving null is an expected state. After this PR,
_getCounterpartUrl unconditionally calls getUrl().getValue(), which will throw NPE if the url field
is null (e.g., missing field during deserialization or not set programmatically). Similar unguarded
dereferences were added/updated in sandbox code paths when building outbound URLs.

core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java[11-19]
core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java[231-236]
core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java[300-303]
sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceOrchestrator.java[192-216]
sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java[211-220]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
`CounterpartConfiguration.url` is nullable, but several code paths dereference it via `getUrl().getValue()` / `getUrl().isBlank()` without null checks. This can crash the orchestrator/party logic with `NullPointerException` when URL is omitted/missing.

### Issue Context
The code already treats URL as optional in at least one place (`asyncCounterpartNotification` checks `counterpartUrl != null`). After the refactor to a `Url` wrapper, dereferencing `getValue()` becomes unsafe if `url` is null.

### Fix Focus Areas
- core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java[11-19]
- core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java[300-303]
- sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceOrchestrator.java[192-216]
- sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java[211-220]

### What to change
- Ensure `CounterpartConfiguration.url` is never null (e.g., initialize to `Url.ofTrusted("")`, enforce non-null in setters/constructors, and/or add Jackson defaulting for missing fields).
- Add defensive handling where URLs are used (e.g., throw a `UserFacingException` with a clear message when URL is required but missing, rather than NPE).
- Prefer a single helper like `String baseUrl = Optional.ofNullable(getUrl()).map(Url::getValue).orElse("");` where empty is acceptable.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools



Remediation recommended

2. Url validation bypassed by Jackson 🐞
Description
Url is documented as “validated”, but Jackson deserialization uses @JsonCreator Url.ofTrusted which
performs no validation, so invalid URLs can enter CounterpartConfiguration.url via
SandboxConfiguration.fromJsonNode. This undermines the new validation rules (including the '?'
restriction) for persisted/config-sourced data.
Code

core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java[R47-50]

+  @JsonCreator
+  public static Url ofTrusted(String url) {
+    return new Url(url != null ? url : "");
+  }
Evidence
Url’s class-level documentation claims instances are validated on construction, but the @JsonCreator
factory ofTrusted just wraps the string. SandboxConfiguration.fromJsonNode uses Jackson
(treeToValue) to materialize configuration objects (including CounterpartConfiguration.url), so
deserialization will accept invalid URL strings without calling Url.validate.

core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java[12-50]
sandbox/src/main/java/org/dcsa/conformance/sandbox/configuration/SandboxConfiguration.java[35-38]
core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java[11-19]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
`Url` is introduced as a validated value object, but Jackson deserialization uses `@JsonCreator Url.ofTrusted(...)`, which does not validate. As a result, configs loaded via Jackson can contain invalid URLs while the type suggests they are validated.

### Issue Context
`sandbox.configuration.SandboxConfiguration.fromJsonNode` uses `OBJECT_MAPPER.treeToValue(...)`, which will deserialize the `url` field into the new `Url` type using `@JsonCreator`.

### Fix Focus Areas
- core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java[12-85]
- sandbox/src/main/java/org/dcsa/conformance/sandbox/configuration/SandboxConfiguration.java[35-38]
- core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java[11-19]

### What to change
Choose one:
1) **Make deserialization validated**: replace `@JsonCreator` with a creator that validates (if you can determine the validation flags at this boundary) or implement a custom Jackson deserializer that validates with appropriate policy.
2) **Stop claiming validation**: if validation cannot happen at deserialization time, update `Url` JavaDoc and naming to remove the “guaranteed valid” contract (and ensure validation is always enforced before use).
3) **Validate at load boundary**: after `SandboxConfiguration.fromJsonNode(...)`, explicitly validate all loaded counterpart URLs (including query-param restriction) and fail fast with a `UserFacingException` if invalid.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


3. Local URLs can be relative 🐞
Description
Url.validate does not require an absolute http(s) URL when allowHttpLocalhost is true, so relative
or non-http URIs can pass validation in localhost mode and later fail when the system builds
HttpRequests from them. This can break sandbox operation in local environments.
Code

core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java[R60-85]

+  public static void validate(String url, boolean allowHttpLocalhost, boolean allowEmpty) throws UserFacingException {
+    if (url.isEmpty()) {
+      if (allowEmpty) {
+        return;
+      }
+      throw new UserFacingException("The application base URL must not be empty: connecting to your application is not optional for this standard and role.");
+    }
+    try {
+      new URI(url);
+    } catch (URISyntaxException e) {
+      throw new UserFacingException("The URL format is not correct", e);
+    }
+    if (url.contains("?")) {
+      throw new UserFacingException("The URL must not contain query parameters (question marks)");
+    }
+    if (!allowHttpLocalhost) {
+      String lowerCaseUrl = url.toLowerCase();
+      if (!lowerCaseUrl.startsWith("https://")) {
+        throw new UserFacingException("The URL must use HTTPS instead of plain HTTP");
+      }
+      if (Stream.of("https://localhost/", "https://localhost:", "https://127.")
+          .anyMatch(lowerCaseUrl::startsWith)) {
+        throw new UserFacingException("The URL cannot be set to a local address");
+      }
+    }
+  }
Evidence
When allowHttpLocalhost is true, Url.validate only checks URI syntax and the absence of '?', but
does not enforce http/https scheme or absoluteness. ConformanceWebuiHandler sets allowHttpLocalhost
based on a localhost sandbox base URL and then stores the provided URL; later, outbound requests are
created with HttpRequest.newBuilder().uri(URI.create(url)), which will throw if the URI is not
absolute (e.g., "example.com/..." or "file:///...").

core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java[60-85]
sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java[343-365]
sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceSandbox.java[831-838]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
In localhost-allowed mode, `Url.validate` accepts any syntactically valid `URI`, including relative references and non-http schemes. These values can later break HTTP request construction (and are not meaningful as base URLs).

### Issue Context
`ConformanceWebuiHandler` chooses `allowHttpLocalhost` for local sandboxes and calls `Url.validate(...)`. Outbound requests ultimately use `HttpRequest.newBuilder().uri(URI.create(url))`, which expects an absolute URI.

### Fix Focus Areas
- core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java[60-85]
- sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java[343-365]
- sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceSandbox.java[831-838]

### What to change
- Enhance `Url.validate` to require an **absolute** URL with **http/https** scheme in all cases.
 - When `allowHttpLocalhost` is false: keep requiring `https://`.
 - When `allowHttpLocalhost` is true: allow both `http://` and `https://`, but still require `uri.isAbsolute()` and a non-empty host.
- Consider rejecting other schemes explicitly (e.g., `file:`, `jar:`, `javascript:`) even in localhost mode.
- Add tests for relative URLs and non-http schemes to ensure they are rejected.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


Grey Divider

ⓘ The new review experience is currently in Beta. Learn more

Grey Divider

Qodo Logo

private String _getCounterpartUrl(
CounterpartConfiguration counterpartConfiguration, String method, String path) {
var url = counterpartConfiguration.getUrl() + path;
var url = counterpartConfiguration.getUrl().getValue() + path;
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Action required

1. Null url npe risk 🐞 Bug ☼ Reliability

ConformanceParty._getCounterpartUrl dereferences counterpartConfiguration.getUrl().getValue()
without checking for null, but other code paths treat the URL as nullable, so a missing/omitted URL
can now crash with a NullPointerException. The same dereference pattern exists in sandbox components
when composing notification/config URLs.
Agent Prompt
### Issue description
`CounterpartConfiguration.url` is nullable, but several code paths dereference it via `getUrl().getValue()` / `getUrl().isBlank()` without null checks. This can crash the orchestrator/party logic with `NullPointerException` when URL is omitted/missing.

### Issue Context
The code already treats URL as optional in at least one place (`asyncCounterpartNotification` checks `counterpartUrl != null`). After the refactor to a `Url` wrapper, dereferencing `getValue()` becomes unsafe if `url` is null.

### Fix Focus Areas
- core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java[11-19]
- core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java[300-303]
- sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceOrchestrator.java[192-216]
- sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java[211-220]

### What to change
- Ensure `CounterpartConfiguration.url` is never null (e.g., initialize to `Url.ofTrusted("")`, enforce non-null in setters/constructors, and/or add Jackson defaulting for missing fields).
- Add defensive handling where URLs are used (e.g., throw a `UserFacingException` with a clear message when URL is required but missing, rather than NPE).
- Prefer a single helper like `String baseUrl = Optional.ofNullable(getUrl()).map(Url::getValue).orElse("");` where empty is acceptable.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR updates URL handling across the conformance sandbox by replacing raw String URLs with a validated Url value object, and by centralizing URL validation logic in core.

Changes:

  • Introduces core.toolkit.Url (Jackson-serializable) and moves URL validation into it.
  • Updates CounterpartConfiguration.url from String to Url and adjusts URL usages (getValue(), isBlank()) accordingly.
  • Updates sandbox UI handler and orchestrator HTTP request construction to use the new Url type.

Reviewed changes

Copilot reviewed 5 out of 5 changed files in this pull request and generated 5 comments.

Show a summary per file
File Description
sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java Uses Url for counterpart URLs, validates external party URL via Url.validate, and returns URL strings via getValue().
sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceOrchestrator.java Builds notification URL using counterpartConfiguration.getUrl().getValue().
core/src/main/java/org/dcsa/conformance/core/toolkit/Url.java New URL value object with validation and Jackson string serialization.
core/src/main/java/org/dcsa/conformance/core/party/CounterpartConfiguration.java Changes url field type to Url and removes legacy validation method.
core/src/main/java/org/dcsa/conformance/core/party/ConformanceParty.java Updates URL checks/concatenation to use Url (isBlank, getValue).
Comments suppressed due to low confidence (1)

sandbox/src/main/java/org/dcsa/conformance/sandbox/ConformanceWebuiHandler.java:408

  • When the orchestrator is inactive, orchestratorUrl is derived by trimming "/party//api" from externalPartyCounterpartConfig.getUrl(). If externalPartyUrl is allowed to be empty for the role (allowEmptyUrl=true) or the provided URL does not match the expected suffix, this substring calculation can throw StringIndexOutOfBoundsException or produce an incorrect orchestratorUrl. Consider skipping this derivation when the URL is blank, and/or verifying the expected suffix before trimming (and failing with a user-facing error if it’s not present).
          .setOrchestratorUrl(
              externalPartyCounterpartConfig
                  .getUrl()
                  .getValue()
                  .substring(
                      0,
                      externalPartyCounterpartConfig.getUrl().length()
                          - "/party/%s/api"
                              .formatted(externalPartyCounterpartConfig.getName())
                              .length()));

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines 208 to 219
CounterpartConfiguration externalPartyCounterpartConfig =
sandboxConfiguration.getExternalPartyCounterpartConfiguration();

ObjectNode jsonSandboxConfig = OBJECT_MAPPER
.createObjectNode()
.put(SANDBOX_ID, sandboxConfiguration.getId())
.put("sandboxName", sandboxConfiguration.getName())
.put("sandboxUrl", sandboxPartyCounterpartConfig.getUrl())
.put("sandboxUrl", sandboxPartyCounterpartConfig.getUrl().getValue())
.put("sandboxAuthHeaderName", sandboxConfiguration.getAuthHeaderName())
.put("sandboxAuthHeaderValue", sandboxConfiguration.getAuthHeaderValue())
.put("externalPartyUrl", externalPartyCounterpartConfig.getUrl())
.put("externalPartyUrl", externalPartyCounterpartConfig.getUrl().getValue())
.put("externalPartyAuthHeaderName", externalPartyCounterpartConfig.getAuthHeaderName())
Copy link

Copilot AI Apr 13, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

_getSandboxConfig() dereferences externalPartyCounterpartConfig.getUrl() without checking if getExternalPartyCounterpartConfiguration() returned null. For all-in-one sandboxes (both parties in the sandbox), getExternalPartyCounterpartConfiguration() can be null, which will cause a NullPointerException when building the JSON response. Consider guarding for null and returning empty strings (or omitting the external-party fields) in that case.

Copilot uses AI. Check for mistakes.
Comment on lines 203 to 211
waitingForBiConsumer.accept(
partyName, "perform action '%s'".formatted(nextAction.getActionTitle()));

asyncWebClient.accept(
new ConformanceWebRequest(
"GET",
counterpartConfiguration.getUrl() + "/conformance/notification",
counterpartConfiguration.getUrl().getValue() + "/conformance/notification",
Collections.emptyMap(),
counterpartConfiguration.getAuthHeaderName().isBlank()
Copy link

Copilot AI Apr 13, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

notifyNextActionParty() now concatenates counterpartConfiguration.getUrl().getValue() without checking for null/blank URLs. Some standards/roles allow an empty external-party URL (no notifications), and Url can also be null if missing from persisted config; either case will lead to an invalid request or NullPointerException here. Consider skipping the outbound notification when the URL is null/blank (similar to other no-notification paths) or treating that counterpart as manual mode for notification purposes.

Copilot uses AI. Check for mistakes.
private String _getCounterpartUrl(
CounterpartConfiguration counterpartConfiguration, String method, String path) {
var url = counterpartConfiguration.getUrl() + path;
var url = counterpartConfiguration.getUrl().getValue() + path;
Copy link

Copilot AI Apr 13, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

_getCounterpartUrl() assumes counterpartConfiguration.getUrl() is non-null and calls getValue() unconditionally. Elsewhere (e.g., asyncCounterpartNotification) the code explicitly allows a null/blank URL, so this can still throw NullPointerException if a request is attempted with an unconfigured counterpart. Consider failing fast with a clear exception when url is null/blank, or ensuring url is always initialized (e.g., Url.ofTrusted("") at deserialization time).

Suggested change
var url = counterpartConfiguration.getUrl().getValue() + path;
var counterpartUrl = counterpartConfiguration.getUrl();
var counterpartUrlValue = counterpartUrl == null ? null : counterpartUrl.getValue();
if (counterpartUrlValue == null || counterpartUrlValue.isBlank()) {
throw new IllegalStateException(
"Counterpart URL is not configured for counterpart '"
+ counterpartConfiguration.getName()
+ "' when creating request "
+ method
+ " "
+ path);
}
var url = counterpartUrlValue + path;

Copilot uses AI. Check for mistakes.
Comment on lines +60 to +66
public static void validate(String url, boolean allowHttpLocalhost, boolean allowEmpty) throws UserFacingException {
if (url.isEmpty()) {
if (allowEmpty) {
return;
}
throw new UserFacingException("The application base URL must not be empty: connecting to your application is not optional for this standard and role.");
}
Copy link

Copilot AI Apr 13, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Url.validate() calls url.isEmpty() without a null check. Since Url.of(...) and validate(...) are public APIs, passing a null url will currently throw a NullPointerException rather than a UserFacingException. Consider explicitly handling null (treat as empty when allowEmpty=true, otherwise throw a UserFacingException with a clear message).

Copilot uses AI. Check for mistakes.
Comment on lines +35 to +85
public static Url of(String url, boolean allowHttpLocalhost, boolean allowEmpty) throws UserFacingException {
validate(url, allowHttpLocalhost, allowEmpty);
return new Url(url);
}

/**
* Creates a URL without validation. Use only when the URL comes from a trusted source
* or when deserializing from JSON (validation should happen at the application boundary).
*
* @param url the URL string
* @return a Url instance
*/
@JsonCreator
public static Url ofTrusted(String url) {
return new Url(url != null ? url : "");
}

/**
* Validates a URL string without creating a Url object.
*
* @param url the URL string to validate
* @param allowHttpLocalhost whether to allow HTTP and localhost URLs
* @param allowEmpty whether to allow empty URLs
* @throws UserFacingException if the URL is invalid
*/
public static void validate(String url, boolean allowHttpLocalhost, boolean allowEmpty) throws UserFacingException {
if (url.isEmpty()) {
if (allowEmpty) {
return;
}
throw new UserFacingException("The application base URL must not be empty: connecting to your application is not optional for this standard and role.");
}
try {
new URI(url);
} catch (URISyntaxException e) {
throw new UserFacingException("The URL format is not correct", e);
}
if (url.contains("?")) {
throw new UserFacingException("The URL must not contain query parameters (question marks)");
}
if (!allowHttpLocalhost) {
String lowerCaseUrl = url.toLowerCase();
if (!lowerCaseUrl.startsWith("https://")) {
throw new UserFacingException("The URL must use HTTPS instead of plain HTTP");
}
if (Stream.of("https://localhost/", "https://localhost:", "https://127.")
.anyMatch(lowerCaseUrl::startsWith)) {
throw new UserFacingException("The URL cannot be set to a local address");
}
}
}
Copy link

Copilot AI Apr 13, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The new Url value object introduces non-trivial validation behavior (HTTPS vs localhost rules, query-parameter rejection, allowEmpty handling). Adding focused unit tests for Url.validate/of (including Jackson round-trip) would help prevent regressions and clarify the expected rules.

Copilot uses AI. Check for mistakes.
Copy link
Copy Markdown
Collaborator

@pedrocarvalhodcsa pedrocarvalhodcsa left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All seems good. Just take a look at the comments from Copilot and the other AI bot to see if they make sense and they need changes

/**
* Returns the length of the URL string.
*/
public int length() {
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is this method used?



@Override
public String toString() {
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we need the toString, equals and hashCode?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants