Skip to content

Commit

Permalink
Enforce no-op on submit buttons with formmethod=dialog. (#3075)
Browse files Browse the repository at this point in the history
* Enforce no-op on submit buttons with formmethod=dialog.

* Properly resolve referenced forms. (#3094)

* Properly resolve referenced forms.

* Clarify variable.

* Cast elt to avoid TS exceptions.

* Refactor for JSDoc.

* Clarify shouldCancel.

* Remove complicated JSDoc in favor of ts-ignore.

* More coverage for button scenarios.

* Use properties instead of matching.

* Mention reset button change.

* Mention formmethod=dialog change.
  • Loading branch information
geoffrey-eisenbarth authored Jan 9, 2025
1 parent f46989b commit 9fcb5c5
Show file tree
Hide file tree
Showing 4 changed files with 18 additions and 43 deletions.
3 changes: 2 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@

## [2.0.5] - 2025-??-??

* Using `<button hx-verb="/endpoint" type="reset">` will now reset the associated form (after submitting to `/endpoint`).
* Using `<button hx-verb="/endpoint" type="reset">` will now reset the associated form (after submitting to `/endpoint`)
* Using `<button formmethod="dialog">` will no longer submit its associated form

## [2.0.4] - 2024-12-13

Expand Down
6 changes: 4 additions & 2 deletions src/htmx.js
Original file line number Diff line number Diff line change
Expand Up @@ -4219,9 +4219,11 @@ var htmx = (function() {

const buttonVerb = getRawAttribute(submitter, 'formmethod')
if (buttonVerb != null) {
// ignore buttons with formmethod="dialog"
if (buttonVerb.toLowerCase() !== 'dialog') {
if (VERBS.includes(buttonVerb.toLowerCase())) {
verb = (/** @type HttpVerb */(buttonVerb))
} else {
maybeCall(resolve)
return promise
}
}
}
Expand Down
26 changes: 6 additions & 20 deletions test/core/ajax.js
Original file line number Diff line number Diff line change
Expand Up @@ -1248,32 +1248,18 @@ describe('Core htmx AJAX Tests', function() {
values.should.deep.equal({ t1: 'textValue', b1: ['inputValue', 'buttonValue'], s1: 'selectValue' })
})

it('handles form post with button formmethod dialog properly', function() {
var values
it('properly handles buttons with formmethod=dialog', function() {
var request = false
this.server.respondWith('POST', '/test', function(xhr) {
values = getParameters(xhr)
xhr.respond(200, {}, '')
})

make('<dialog><form hx-post="/test"><button id="submit" formmethod="dialog" name="foo" value="bar">submit</button></form></dialog>')

byId('submit').click()
this.server.respond()
values.should.deep.equal({ foo: 'bar' })
})

it('handles form get with button formmethod dialog properly', function() {
var responded = false
this.server.respondWith('GET', '/test', function(xhr) {
responded = true
xhr.respond(200, {}, '')
request = true
xhr.respond(200, {}, '<button>Bar</button>')
})

make('<dialog><form hx-get="/test"><button id="submit" formmethod="dialog">submit</button></form></dialog>')
make('<dialog><form hx-post="/test"><button id="submit" formmethod="dialog" name="foo" value="bar">Submit</button></form></dialog>')

byId('submit').click()
this.server.respond()
responded.should.equal(true)
request.should.equal(false)
})

it('can associate submit buttons from outside a form with the current version of the form after swap', function() {
Expand Down
26 changes: 6 additions & 20 deletions test/core/shadowdom.js
Original file line number Diff line number Diff line change
Expand Up @@ -1254,32 +1254,18 @@ describe('Core htmx Shadow DOM Tests', function() {
values.should.deep.equal({ t1: 'textValue', b1: ['inputValue', 'buttonValue'], s1: 'selectValue' })
})

it('handles form post with button formmethod dialog properly', function() {
var values
it('properly handles buttons with formmethod=dialog', function() {
var request = false
this.server.respondWith('POST', '/test', function(xhr) {
values = getParameters(xhr)
xhr.respond(200, {}, '')
})

make('<dialog><form hx-post="/test"><button id="submit" formmethod="dialog" name="foo" value="bar">submit</button></form></dialog>')

byId('submit').click()
this.server.respond()
values.should.deep.equal({ foo: 'bar' })
})

it('handles form get with button formmethod dialog properly', function() {
var responded = false
this.server.respondWith('GET', '/test', function(xhr) {
responded = true
xhr.respond(200, {}, '')
request = true
xhr.respond(200, {}, '<button>Bar</button>')
})

make('<dialog><form hx-get="/test"><button id="submit" formmethod="dialog">submit</button></form></dialog>')
make('<dialog><form hx-post="/test"><button id="submit" formmethod="dialog" name="foo" value="bar">Submit</button></form></dialog>')

byId('submit').click()
this.server.respond()
responded.should.equal(true)
request.should.equal(false)
})

it('can associate submit buttons from outside a form with the current version of the form after swap', function() {
Expand Down

0 comments on commit 9fcb5c5

Please sign in to comment.