[ENGG-5091] fix: content-type sent when body is empty#4055
[ENGG-5091] fix: content-type sent when body is empty#4055wrongsahil merged 5 commits intomasterfrom
Conversation
WalkthroughThis PR refactors the request body state management architecture by removing the context-based Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes
Possibly related PRs
Suggested reviewers
Pre-merge checks and finishing touches❌ Failed checks (2 warnings)
✅ Passed checks (1 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
📜 Recent review detailsConfiguration used: Organization UI Review profile: CHILL Plan: Pro 📒 Files selected for processing (4)
💤 Files with no reviewable changes (1)
🚧 Files skipped from review as they are similar to previous changes (1)
🧰 Additional context used🧠 Learnings (4)📚 Learning: 2025-11-25T09:03:46.345ZApplied to files:
📚 Learning: 2025-09-09T09:07:32.092ZApplied to files:
📚 Learning: 2025-12-11T06:43:01.328ZApplied to files:
📚 Learning: 2025-10-08T15:27:08.928ZApplied to files:
🔇 Additional comments (9)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 9
🧹 Nitpick comments (1)
app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/multipart-form-body-renderer.tsx (1)
1-1: Use PascalCase for React import.The import uses lowercase
reactwhich is inconsistent with the rest of the codebase. While it works, convention is to useReactwith PascalCase.🔎 Apply this diff:
-import react, { useCallback } from "react"; +import React, { useCallback } from "react";And update the component type:
-export const MultipartFormBodyRenderer: react.FC<{ +export const MultipartFormBodyRenderer: React.FC<{
📜 Review details
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (8)
app/src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx(7 hunks)app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/form-body-renderer.tsx(1 hunks)app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/multipart-form-body-renderer.tsx(1 hunks)app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/raw-body-renderer.tsx(2 hunks)app/src/features/apiClient/screens/apiClient/components/views/components/request/request-body-types.ts(0 hunks)app/src/features/apiClient/screens/apiClient/components/views/http/HttpClientView.tsx(2 hunks)app/src/features/apiClient/screens/apiClient/components/views/http/components/HttpRequestTabs/HttpRequestTabs.tsx(1 hunks)app/src/features/apiClient/screens/apiClient/utils.ts(1 hunks)
💤 Files with no reviewable changes (1)
- app/src/features/apiClient/screens/apiClient/components/views/components/request/request-body-types.ts
🧰 Additional context used
🧠 Learnings (6)
📚 Learning: 2025-10-08T15:27:08.928Z
Learnt from: Aarushsr12
Repo: requestly/requestly PR: 3650
File: app/src/features/apiClient/screens/apiClient/utils.ts:280-306
Timestamp: 2025-10-08T15:27:08.928Z
Learning: In `app/src/features/apiClient/screens/apiClient/utils.ts`, when parsing cURL commands with multipart form files (values starting with "@"), the `generateMultipartFormKeyValuePairs` function intentionally creates `FormDataKeyValuePair` entries with an empty `value` array (type: FILE). The file path from cURL is not extracted or stored. Instead, the key is preserved to show in the UI table, and users select the actual file later using a file picker.
Applied to files:
app/src/features/apiClient/screens/apiClient/utils.tsapp/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/multipart-form-body-renderer.tsxapp/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/form-body-renderer.tsx
📚 Learning: 2025-11-20T14:37:21.459Z
Learnt from: nafees87n
Repo: requestly/requestly PR: 3801
File: app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestExecutor.ts:180-194
Timestamp: 2025-11-20T14:37:21.459Z
Learning: In HttpRequestExecutor.execute method in `app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestExecutor.ts`, iterationContext parameter must be required (not optional) with no defaults or falsy checks. TypeScript should enforce that callers provide this data, per maintainer iostreamer-X's requirement.
Applied to files:
app/src/features/apiClient/screens/apiClient/utils.ts
📚 Learning: 2025-10-22T22:57:45.959Z
Learnt from: mustafa-sayyed
Repo: requestly/requestly PR: 3723
File: app/src/features/apiClient/screens/apiClient/components/views/http/components/HttpRequestTabs/HttpRequestTabs.tsx:146-151
Timestamp: 2025-10-22T22:57:45.959Z
Learning: In the API Client Scripts tab (app/src/features/apiClient/screens/apiClient/components/views/http/components/HttpRequestTabs/HttpRequestTabs.tsx), the dot indicator should only appear when scripts are present (count > 0). When no scripts exist, the dot should not be rendered. This is the intended behavior per issue #3731.
Applied to files:
app/src/features/apiClient/screens/apiClient/components/views/http/components/HttpRequestTabs/HttpRequestTabs.tsxapp/src/features/apiClient/screens/apiClient/components/views/http/HttpClientView.tsx
📚 Learning: 2025-10-10T11:08:23.369Z
Learnt from: nafees87n
Repo: requestly/requestly PR: 3655
File: app/src/features/apiClient/screens/apiClient/components/views/components/Collection/components/CollectionRunnerView/components/RunResultView/RunResultContainer/RunResultContainer.tsx:426-426
Timestamp: 2025-10-10T11:08:23.369Z
Learning: In the file `app/src/features/apiClient/screens/apiClient/components/views/components/Collection/components/CollectionRunnerView/components/RunResultView/RunResultContainer/RunResultContainer.tsx`, the `destroyInactiveTabPane={true}` setting is intentional. The loss of state (expandedKeys, scroll position) when switching tabs is acceptable for now and will be addressed in future work.
Applied to files:
app/src/features/apiClient/screens/apiClient/components/views/http/components/HttpRequestTabs/HttpRequestTabs.tsx
📚 Learning: 2025-11-25T09:03:46.345Z
Learnt from: CR
Repo: requestly/requestly PR: 0
File: .cursorrules:0-0
Timestamp: 2025-11-25T09:03:46.345Z
Learning: Use TypeScript where applicable in the Requestly project
Applied to files:
app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/form-body-renderer.tsxapp/src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx
📚 Learning: 2025-12-11T06:43:01.328Z
Learnt from: rohanmathur91
Repo: requestly/requestly PR: 4000
File: app/src/features/apiClient/slices/multiWorkspaceView/helpers/ApiClientContextRegistry/hooks.ts:6-14
Timestamp: 2025-12-11T06:43:01.328Z
Learning: In app/src/features/apiClient/slices/multiWorkspaceView/helpers/ApiClientContextRegistry/hooks.ts, the useApiClientFeatureContext hook uses useMemo without reactivity intentionally. Contexts are expected to be registered before component mount, and reactivity to registry updates is not needed.
Applied to files:
app/src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx
🧬 Code graph analysis (1)
app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/raw-body-renderer.tsx (2)
app/src/features/apiClient/helpers/variableResolver/variable-resolver.ts (1)
useScopedVariables(283-314)app/src/hooks/useDebounce.ts (1)
useDebounce(4-20)
🔇 Additional comments (5)
app/src/features/apiClient/screens/apiClient/components/views/http/components/HttpRequestTabs/HttpRequestTabs.tsx (1)
116-124: LGTM!The simplified
RequestBodyusage with directbodyandcontentTypeprops is cleaner than the previous approach. The component now encapsulates content-type management internally while still allowing parent state updates viasetRequestEntry.app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/raw-body-renderer.tsx (1)
9-29: LGTM!Clean refactor to the prop-driven callback pattern. The
handleContentChangecallback properly propagates changes with the content type, and the debounced handler has correct dependencies.app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/multipart-form-body-renderer.tsx (1)
7-23: LGTM!The refactor to use
handleContentChangecallback is clean and consistent with the other body renderers. The implementation correctly propagates content type changes.app/src/features/apiClient/screens/apiClient/components/views/components/request/renderers/form-body-renderer.tsx (1)
7-26: LGTM on the refactor pattern.The prop-driven approach with
handleContentChangecallback is consistent with the other body renderers and properly propagates content type with body updates.app/src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx (1)
82-258: Overall approach is sound but needs cleanup.The refactor successfully moves content-type management into
RequestBodyand properly integrates withuseAutogenerateStorefor header management. The core logic for conditionally setting Content-Type headers based on body presence aligns with the PR objective. After removing debug logs, dead code, and fixing the missing dependency, this is a solid implementation.
...lient/screens/apiClient/components/views/components/request/renderers/form-body-renderer.tsx
Outdated
Show resolved
Hide resolved
...src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx
Outdated
Show resolved
Hide resolved
...src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx
Show resolved
Hide resolved
...src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx
Outdated
Show resolved
Hide resolved
...src/features/apiClient/screens/apiClient/components/views/components/request/RequestBody.tsx
Outdated
Show resolved
Hide resolved
app/src/features/apiClient/screens/apiClient/components/views/http/HttpClientView.tsx
Outdated
Show resolved
Hide resolved
app/src/features/apiClient/screens/apiClient/components/views/http/HttpClientView.tsx
Outdated
Show resolved
Hide resolved
There was a problem hiding this comment.
Actionable comments posted: 1
📜 Review details
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (2)
app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestExecutor.ts(1 hunks)app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestPreparationService.ts(1 hunks)
🧰 Additional context used
🧠 Learnings (1)
📚 Learning: 2025-11-20T14:37:21.459Z
Learnt from: nafees87n
Repo: requestly/requestly PR: 3801
File: app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestExecutor.ts:180-194
Timestamp: 2025-11-20T14:37:21.459Z
Learning: In HttpRequestExecutor.execute method in `app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestExecutor.ts`, iterationContext parameter must be required (not optional) with no defaults or falsy checks. TypeScript should enforce that callers provide this data, per maintainer iostreamer-X's requirement.
Applied to files:
app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestExecutor.tsapp/src/features/apiClient/helpers/httpRequestExecutor/httpRequestPreparationService.ts
🔇 Additional comments (1)
app/src/features/apiClient/helpers/httpRequestExecutor/httpRequestPreparationService.ts (1)
200-204: Remove the review comment—the code is correct and type-safe.The condition correctly handles all valid request body types. According to the type definitions,
RequestBodycan only be:string,KeyValuePair[],FormDataKeyValuePair[],undefined, ornull. The code safely normalizes empty bodies:
!renderedEntry?.request?.bodycatchesundefined,null, and empty strings""(which is falsy)renderedEntry.request?.body?.length <= 0catches empty arrays[](which are truthy but havelength === 0) and empty strings (length 0)Both strings and arrays have a
.lengthproperty, so accessing it is type-safe. Empty objects{}cannot occur due to the type system. The logic is sound and properly normalizes all empty body variants before passing to fetch.The "Hacky Fix" comment accurately describes the workaround for fetch automatically setting Content-Type to text/plain for string bodies, but the implementation itself is not problematic.
text/plainif "" body is sentSummary by CodeRabbit
Release Notes
Bug Fixes
Refactor
✏️ Tip: You can customize this high-level summary in your review settings.