Skip to content

fix: resolve variables in HTML documentation export#7768

Open
eeshm wants to merge 1 commit intousebruno:mainfrom
eeshm:fix/html-doc-variable-resolution
Open

fix: resolve variables in HTML documentation export#7768
eeshm wants to merge 1 commit intousebruno:mainfrom
eeshm:fix/html-doc-variable-resolution

Conversation

@eeshm
Copy link
Copy Markdown

@eeshm eeshm commented Apr 15, 2026

Description

fixes : #7636

Fixes HTML documentation export to resolve variable placeholders before rendering docs.

Problem - Generated HTML docs were showing raw placeholders like {{url}}/get instead of resolved values.

Changes

  • Added resolveCollectionForHtmlDocumentation in utils/exporters/html-documentation.
  • Applied resolver in GenerateDocumentation before converting to OpenCollection/YAML.
  • Resolver interpolates request/examples using existing variable scope precedence (global, collection, environment, folder/request vars).

Tests

  • Added html-documentation.spec.js regression tests to verify: no unresolved {{...}} placeholders remain in resolved request fields.

Note : Request execution behavior is unchanged; this only affects docs export output

  • before
image
  • after
Screenshot 2026-04-15 144508

Contribution Checklist:

  • I've used AI significantly to create this pull request
  • The pull request only addresses one issue or adds one feature.
  • The pull request does not introduce any breaking changes
  • I have added screenshots or gifs to help explain the change if applicable.
  • I have read the contribution guidelines.
  • Create an issue and link to the pull request.

Publishing to New Package Managers

Please see here for more information.

Summary by CodeRabbit

  • New Features

    • HTML documentation generation now includes and resolves global environment variables from the active environment configuration. Template placeholders (e.g., {{url}}, {{token}}) are now interpolated throughout request URLs, headers, path parameters, and body content during documentation export.
  • Tests

    • Added comprehensive test coverage validating variable resolution and interpolation across multiple request fields in HTML documentation generation.

Copilot AI review requested due to automatic review settings April 15, 2026 10:02
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai bot commented Apr 15, 2026

Walkthrough

The PR enhances HTML documentation generation by integrating global environment variables into the export process. The GenerateDocumentation component retrieves global environment variables from Redux state and injects them into the collection before export. A new utility function resolves all template placeholders throughout collection requests using computed interpolation variables from global, environment, and request-scoped sources.

Changes

Cohort / File(s) Summary
GenerateDocumentation Component
packages/bruno-app/src/components/Sidebar/Collections/Collection/GenerateDocumentation/index.js
Derives globalEnvironmentVariables from Redux state via memoized selector, injects them into a deep-cloned collection, and calls new resolveCollectionForHtmlDocumentation before transformation. Updates useCallback dependency list to track global environment changes.
HTML Documentation Resolver
packages/bruno-app/src/utils/exporters/html-documentation.js
Adds resolveCollectionForHtmlDocumentation utility that traverses collection items and resolves template placeholders in URLs (with path-parameter interpolation), headers, params, auth objects, body fields (JSON, text, XML, GraphQL, SPARQL, form-encoded, multipart, gRPC, WebSocket), documentation text, and request examples using computed environment and request-scoped variables.
Test Coverage
packages/bruno-app/src/utils/exporters/html-documentation.spec.js
New test file validating placeholder resolution across request URLs, headers, path parameters, and body content using global and environment variables, with assertions ensuring no unresolved template markers remain after processing.

Sequence Diagram

sequenceDiagram
    participant UI as GenerateDocumentation<br/>Component
    participant Redux as Redux<br/>State
    participant Resolver as resolveCollection<br/>ForHtmlDocumentation
    participant Interpolator as Interpolation<br/>Engine
    participant Exporter as HTML<br/>Exporter

    UI->>Redux: Query globalEnvironments<br/>& activeGlobalEnvironmentUid
    Redux-->>UI: Return globalEnvironmentVariables
    UI->>UI: Deep clone collection
    UI->>Resolver: resolveCollection(collectionCopy,<br/>globalEnvironmentVariables)
    
    loop For each request item
        Resolver->>Interpolator: getAllVariables(item)
        Interpolator-->>Resolver: Computed variables<br/>(global + env + request)
        Resolver->>Resolver: Interpolate URL,<br/>headers, params, auth, body
        Resolver->>Resolver: Interpolate examples<br/>(if present)
    end
    
    Resolver-->>UI: Return resolved collection
    UI->>Exporter: Export resolved<br/>collection to HTML
    Exporter-->>UI: HTML documentation
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

Suggested labels

size/M

Suggested reviewers

  • helloanoop
  • lohit-bruno
  • naman-bruno
  • bijin-bruno

Poem

Variables dance through Redux's state 🎭
Global environment, interpolated straight
Templates resolve from URL to body
Documentation blooms, no placeholders to see 🌿
Resolved and ready, exported with glee ✨

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'fix: resolve variables in HTML documentation export' clearly and concisely describes the main change: implementing variable resolution for HTML documentation exports.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

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.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

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

Fixes HTML documentation generation so exported docs render resolved request fields (e.g., URLs) instead of raw {{var}} placeholders, addressing #7636 in the Bruno app documentation exporter flow.

Changes:

  • Added a collection/request resolver for HTML docs export that interpolates variables across requests and examples.
  • Wired the resolver into the “Generate Documentation” flow before converting to OpenCollection/YAML.
  • Added regression tests ensuring exported request fields no longer contain unresolved {{...}} placeholders.

Reviewed changes

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

File Description
packages/bruno-app/src/utils/exporters/html-documentation.js New resolver to interpolate request fields (url/headers/params/body/auth/docs) for HTML docs export.
packages/bruno-app/src/components/Sidebar/Collections/Collection/GenerateDocumentation/index.js Applies resolver during documentation generation and injects global env variables from Redux state.
packages/bruno-app/src/utils/exporters/html-documentation.spec.js Adds tests verifying placeholder resolution for URLs and payload fields.

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

body.xml = interpolateString(body.xml, variables);
break;
case 'graphql':
body.graphql = interpolateString(body.graphql, variables, { escapeJSONStrings: true });
Comment on lines 87 to +90
const collectionCopy = cloneDeep(collection);
collectionCopy.globalEnvironmentVariables = globalEnvironmentVariables;
resolveCollectionForHtmlDocumentation(collectionCopy);

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (1)
packages/bruno-app/src/utils/exporters/html-documentation.spec.js (1)

54-134: Add one edge-path test for example requests (and multipart file parts).

Current coverage is strong for primary request payloads, but this resolver also processes item.examples[].request and multipart entries. A focused test there would reduce regression risk on changed paths.

As per coding guidelines, "Cover both the 'happy path' and the realistically problematic paths."

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@packages/bruno-app/src/utils/exporters/html-documentation.spec.js` around
lines 54 - 134, Add a new unit test exercising
resolveCollectionForHtmlDocumentation that includes an item with non-empty
items[].examples (populate examples[].request with template variables) and a
multipart formdata body containing file-type parts so the resolver's
example-request and multipart file-part paths are covered; assert that variables
in examples[].request (url, headers, body) are resolved (no '{{' remaining) and
that file parts retain expected metadata (e.g., filename/type) after resolution
to prevent regressions in the example-request and multipart handling code paths.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@packages/bruno-app/src/utils/exporters/html-documentation.js`:
- Around line 94-102: The current early return for non-text multipart entries
prevents name interpolation; instead, always set name:
interpolateString(entry.name, variables) for every entry and only skip value
interpolation when entry.type !== 'text' (i.e., preserve the existing behavior
of not interpolating file/binary values). Update the block that references entry
and interpolateString so it returns { ...entry, name:
interpolateString(entry.name, variables), value: (entry.type === 'text' ?
interpolateString(entry.value, variables) : entry.value) } rather than returning
early for non-text entries.

---

Nitpick comments:
In `@packages/bruno-app/src/utils/exporters/html-documentation.spec.js`:
- Around line 54-134: Add a new unit test exercising
resolveCollectionForHtmlDocumentation that includes an item with non-empty
items[].examples (populate examples[].request with template variables) and a
multipart formdata body containing file-type parts so the resolver's
example-request and multipart file-part paths are covered; assert that variables
in examples[].request (url, headers, body) are resolved (no '{{' remaining) and
that file parts retain expected metadata (e.g., filename/type) after resolution
to prevent regressions in the example-request and multipart handling code paths.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 5a0a866c-7c2d-43a3-9097-a431f8994025

📥 Commits

Reviewing files that changed from the base of the PR and between 9822cee and 129bba6.

📒 Files selected for processing (3)
  • packages/bruno-app/src/components/Sidebar/Collections/Collection/GenerateDocumentation/index.js
  • packages/bruno-app/src/utils/exporters/html-documentation.js
  • packages/bruno-app/src/utils/exporters/html-documentation.spec.js

Comment on lines +94 to +102
if (entry.type && entry.type !== 'text') {
return entry;
}

return {
...entry,
name: interpolateString(entry.name, variables),
value: interpolateString(entry.value, variables)
};
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Interpolate multipart field names for non-text entries too.

Line 94 currently returns early for non-text multipart entries, so name placeholders can remain unresolved in exported docs. Keep skipping value interpolation for file/binary parts, but still resolve name.

💡 Proposed fix
-            if (entry.type && entry.type !== 'text') {
-              return entry;
-            }
-
-            return {
-              ...entry,
-              name: interpolateString(entry.name, variables),
-              value: interpolateString(entry.value, variables)
-            };
+            const interpolatedEntry = {
+              ...entry,
+              name: interpolateString(entry.name, variables)
+            };
+
+            if (entry.type && entry.type !== 'text') {
+              return interpolatedEntry;
+            }
+
+            return {
+              ...interpolatedEntry,
+              value: interpolateString(entry.value, variables)
+            };
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
if (entry.type && entry.type !== 'text') {
return entry;
}
return {
...entry,
name: interpolateString(entry.name, variables),
value: interpolateString(entry.value, variables)
};
const interpolatedEntry = {
...entry,
name: interpolateString(entry.name, variables)
};
if (entry.type && entry.type !== 'text') {
return interpolatedEntry;
}
return {
...interpolatedEntry,
value: interpolateString(entry.value, variables)
};
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@packages/bruno-app/src/utils/exporters/html-documentation.js` around lines 94
- 102, The current early return for non-text multipart entries prevents name
interpolation; instead, always set name: interpolateString(entry.name,
variables) for every entry and only skip value interpolation when entry.type !==
'text' (i.e., preserve the existing behavior of not interpolating file/binary
values). Update the block that references entry and interpolateString so it
returns { ...entry, name: interpolateString(entry.name, variables), value:
(entry.type === 'text' ? interpolateString(entry.value, variables) :
entry.value) } rather than returning early for non-text entries.

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

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Global variables not resolved in generated HTML documentation (URL remains as placeholder

2 participants