Skip to content

invalid merge patch#1627

Merged
arcuri82 merged 6 commits into
masterfrom
http-invalid-merge-patch
Jul 8, 2026
Merged

invalid merge patch#1627
arcuri82 merged 6 commits into
masterfrom
http-invalid-merge-patch

Conversation

@omursahin

@omursahin omursahin commented Jul 3, 2026

Copy link
Copy Markdown
Collaborator
   /**
    * Calls:
    * 1 - (201) POST:/api/mergepatch/buggy
    * 2 - (200) GET:/api/mergepatch/buggy/{id}
    * 3 - (200) PATCH:/api/mergepatch/buggy/{id}
    * 4 - (200) GET:/api/mergepatch/buggy/{id}
    * Found 1 potential fault of type-code 922
    */
    @Test @Timeout(60)
    fun test_10_getOnBuggiInvalidMergePatch()  {
        
        val dto_MergePatchResource_1 = MergePatchResource()
        dto_MergePatchResource_1.setValue(526)
        
        val res_0: ValidatableResponse = given().accept("*/*")
                .header("x-EMextraHeader123", "")
                .contentType("application/json")
                .body(dto_MergePatchResource_1)
                .post("${baseUrlOfSut}/api/mergepatch/buggy")
                .then()
                .statusCode(201)
                .assertThat()
                .contentType("application/json")
                .body("'name'", nullValue())
                .body("'value'", numberMatches(526))
        val location_buggy__2 = res_0.extract().header("location")
        assertTrue(isValidURIorEmpty(location_buggy__2));
        
        given().accept("*/*")
                .header("x-EMextraHeader123", "")
                .get(resolveLocation(location_buggy__2, baseUrlOfSut + "/api/mergepatch/buggy/856"))
                .then()
                .statusCode(200)
                .assertThat()
                .contentType("application/json")
                .body("'name'", nullValue())
                .body("'value'", numberMatches(526))
        
        // Fault922. JSON Merge Patch changes untouched fields.
        val dto_MergeRequest_4 = MergeRequest()
        
        given().accept("*/*")
                .header("x-EMextraHeader123", "")
                .contentType("application/merge-patch+json")
                .body(dto_MergeRequest_4)
                .patch(resolveLocation(location_buggy__2, baseUrlOfSut + "/api/mergepatch/buggy/856?EMextraParam123=42"))
                .then()
                .statusCode(200)
                .assertThat()
                .contentType("application/json")
                .body("'name'", nullValue())
                .body("'value'", nullValue())
        
        given().accept("*/*")
                .header("x-EMextraHeader123", "")
                .get(resolveLocation(location_buggy__2, baseUrlOfSut + "/api/mergepatch/buggy/856"))
                .then()
                .statusCode(200)
                .assertThat()
                .contentType("application/json")
                .body("'name'", nullValue())
                .body("'value'", nullValue())
    }
    

@omursahin omursahin requested a review from arcuri82 July 7, 2026 12:45
if (before.auth.isDifferentFrom(after.auth)) return false

// merge-patch bodies are JSON (incl. application/merge-patch+json)
val bodyParam = patch.parameters.find { it is BodyParam } as BodyParam?

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.

here you should explicitly check for application/merge-patch+json or application/json. other formats such as application/json-patch+json would be wrong, and so cannot just use isJson()

if (!StatusGroup.G_2xx.isInGroup(resPatch.getStatusCode())) return false
if (!StatusGroup.G_2xx.isInGroup(resAfter.getStatusCode())) return false

val untouched = extractModifiedFieldNames(patch) - extractSentFieldNames(patch)

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.

can add the following comment:
If there are flaky fields, eg, timestamps, there could be a different value between the 2 GETs, regardless of the PATCH. However, we are only looking at the fields of PATCH. it would be weird to set a value with a PATCH that the API can change on a whim... not impossible, but most likely very unlikely. so, in theory field flakiness should not be a problem here

)
if (successPatches.isEmpty()) return@forEach

for (candidate in successPatches.sortedBy { it.individual.size() }) {

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.

are we checking this for every possible candidate? or shouldn't we break as soon as we get one that works?

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

@arcuri82 It checks every possible solution. We can return early if we find a fault, if you want, but it can also be valuable to report different combinations of the fault. What do you think?

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.

are we differentiating these potential different cases in the fitness function using the context for the detected faults? if not, then it is no point, as anyway any other new test would be discarded in archive as not improving fitness

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

No, you are right. It will not improve fitness.

)
if (successPatches.isEmpty()) return@forEach

for (candidate in successPatches.sortedBy { it.individual.size() }) {

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.

are we differentiating these potential different cases in the fitness function using the context for the detected faults? if not, then it is no point, as anyway any other new test would be discarded in archive as not improving fitness

@omursahin omursahin requested a review from arcuri82 July 8, 2026 10:28
@arcuri82 arcuri82 merged commit 5cf86a8 into master Jul 8, 2026
31 checks passed
@arcuri82 arcuri82 deleted the http-invalid-merge-patch branch July 8, 2026 11:14
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.

2 participants