From 7bd2ce86a7276fa528e38e64d8511a1fd66af996 Mon Sep 17 00:00:00 2001 From: Kevin McConnell Date: Tue, 28 Feb 2023 11:53:41 +0000 Subject: [PATCH] Rename `isIdempotent` to `isSafe` (#883) The method name was a bit misleading, as what we're actually checking for here is whether the method is [safe][0]. We can also now make use of this method in a couple of places where we clear the snapshot cache after form submissions. The logic there is to clear the cache when performing an operation that is unsafe. [0]: https://developer.mozilla.org/en-US/docs/Glossary/Safe/HTTP --- src/core/drive/form_submission.ts | 10 +++++----- src/core/drive/navigator.ts | 3 +-- src/core/frames/frame_controller.ts | 2 +- src/http/fetch_request.ts | 6 +++--- 4 files changed, 10 insertions(+), 11 deletions(-) diff --git a/src/core/drive/form_submission.ts b/src/core/drive/form_submission.ts index 6eedec1f3..efb75bc01 100644 --- a/src/core/drive/form_submission.ts +++ b/src/core/drive/form_submission.ts @@ -110,8 +110,8 @@ export class FormSubmission { return formEnctypeFromString(this.submitter?.getAttribute("formenctype") || this.formElement.enctype) } - get isIdempotent() { - return this.fetchRequest.isIdempotent + get isSafe() { + return this.fetchRequest.isSafe } get stringFormData() { @@ -151,7 +151,7 @@ export class FormSubmission { // Fetch request delegate prepareRequest(request: FetchRequest) { - if (!request.isIdempotent) { + if (!request.isSafe) { const token = getCookieValue(getMetaContent("csrf-param")) || getMetaContent("csrf-token") if (token) { request.headers["X-CSRF-Token"] = token @@ -239,11 +239,11 @@ export class FormSubmission { } requestMustRedirect(request: FetchRequest) { - return !request.isIdempotent && this.mustRedirect + return !request.isSafe && this.mustRedirect } requestAcceptsTurboStreamResponse(request: FetchRequest) { - return !request.isIdempotent || hasAttribute("data-turbo-stream", this.submitter, this.formElement) + return !request.isSafe || hasAttribute("data-turbo-stream", this.submitter, this.formElement) } get submitsWith() { diff --git a/src/core/drive/navigator.ts b/src/core/drive/navigator.ts index 5165f505d..7579913f1 100644 --- a/src/core/drive/navigator.ts +++ b/src/core/drive/navigator.ts @@ -1,6 +1,5 @@ import { Action } from "../types" import { getVisitAction } from "../../util" -import { FetchMethod } from "../../http/fetch_request" import { FetchResponse } from "../../http/fetch_response" import { FormSubmission } from "./form_submission" import { expandURL, getAnchor, getRequestURL, Locatable, locationIsVisitable } from "../url" @@ -85,7 +84,7 @@ export class Navigator { if (formSubmission == this.formSubmission) { const responseHTML = await fetchResponse.responseHTML if (responseHTML) { - const shouldCacheSnapshot = formSubmission.method == FetchMethod.get + const shouldCacheSnapshot = formSubmission.isSafe if (!shouldCacheSnapshot) { this.view.clearSnapshotCache() } diff --git a/src/core/frames/frame_controller.ts b/src/core/frames/frame_controller.ts index bcf802fe3..cf39a3af6 100644 --- a/src/core/frames/frame_controller.ts +++ b/src/core/frames/frame_controller.ts @@ -268,7 +268,7 @@ export class FrameController frame.delegate.proposeVisitIfNavigatedWithAction(frame, formSubmission.formElement, formSubmission.submitter) frame.delegate.loadResponse(response) - if (formSubmission.method !== FetchMethod.get) { + if (!formSubmission.isSafe) { session.clearCache() } } diff --git a/src/http/fetch_request.ts b/src/http/fetch_request.ts index 767c6f44b..5086392b2 100644 --- a/src/http/fetch_request.ts +++ b/src/http/fetch_request.ts @@ -144,7 +144,7 @@ export class FetchRequest { credentials: "same-origin", headers: this.headers, redirect: "follow", - body: this.isIdempotent ? null : this.body, + body: this.isSafe ? null : this.body, signal: this.abortSignal, referrer: this.delegate.referrer?.href, } @@ -156,8 +156,8 @@ export class FetchRequest { } } - get isIdempotent() { - return this.method == FetchMethod.get + get isSafe() { + return this.method === FetchMethod.get } get abortSignal() {