Description
The ThreadProvider component does not read NEXT_PUBLIC_API_URL and NEXT_PUBLIC_ASSISTANT_ID environment variables, while StreamProvider does. This inconsistency causes the Thread History panel to remain empty when the application is accessed without explicit query parameters in the URL.
Environment
- Version:
main branch (as of latest commit)
- Node.js: v20.x
- Next.js: v14.x
- Browser: Chrome, Firefox (all browsers affected)
Steps to Reproduce
-
Set environment variables in .env.local:
NEXT_PUBLIC_API_URL=http://localhost:8383/api/v1/agent-protocol
NEXT_PUBLIC_ASSISTANT_ID=my-assistant
-
Start the development server:
-
Access the application WITHOUT query parameters:
http://localhost:3000/chat
-
Observe the Thread History panel (left sidebar)
Expected Behavior
- Thread History panel should load and display threads from the API
- The application should use environment variables as default configuration
- Behavior should be consistent with StreamProvider (which correctly reads env vars)
This is the standard Next.js pattern for configuration:
- Environment variables provide defaults
- Query parameters can override defaults
- Users can deploy without hardcoded URLs
Actual Behavior
- Thread History panel shows a loading spinner indefinitely
- No threads are loaded or displayed
- The sidebar remains empty
Workaround: Manually append query parameters to the URL:
http://localhost:3000/chat?apiUrl=http://localhost:8383/api/v1/agent-protocol&assistantId=my-assistant
When query parameters are provided, Thread History works correctly.
Root Cause
StreamProvider (Working) ✅
File: src/providers/Stream.tsx
export function StreamProvider({ children }: PropsWithChildren) {
const envApiUrl: string | undefined = process.env.NEXT_PUBLIC_API_URL;
const envAssistantId: string | undefined = process.env.NEXT_PUBLIC_ASSISTANT_ID;
const [apiUrl] = useQueryState("apiUrl", {
defaultValue: envApiUrl || "",
});
const [assistantId] = useQueryState("assistantId", {
defaultValue: envAssistantId || "",
});
// ...
}
✅ Reads environment variables
✅ Passes them as defaultValue to useQueryState
✅ Works with and without query parameters
ThreadProvider (Broken) ❌
File: src/providers/Thread.tsx (lines 36-40)
export function ThreadProvider({ children }: PropsWithChildren) {
const [apiUrl] = useQueryState("apiUrl"); // ❌ No defaultValue
const [assistantId] = useQueryState("assistantId"); // ❌ No defaultValue
const [threadId] = useQueryState("threadId");
// ...
}
❌ Does NOT read environment variables
❌ No defaultValue provided to useQueryState
❌ Only works when query parameters are explicitly provided
Impact
Users Affected
- Anyone deploying the application with environment-based configuration
- Teams that want clean URLs without query parameters
- Production deployments using Next.js environment variables
Severity
Medium - Core feature (Thread History) is broken in default configuration
Workarounds
-
Manual Query Parameters (user-facing):
- Append
?apiUrl=...&assistantId=... to every URL
- Requires user education and bookmarking
- Not scalable
-
URL Rewriting (server-side):
- Implement redirect rules to inject query parameters
- Adds complexity and fragility
- Doesn't fix the underlying issue
-
Patch ThreadProvider (our temporary solution):
- Modify Thread.tsx to match StreamProvider pattern
- Works correctly but requires maintenance on updates
Proposed Fix
Apply the same pattern used in StreamProvider to ThreadProvider:
export function ThreadProvider({ children }: PropsWithChildren) {
// Read environment variables
const envApiUrl: string | undefined = process.env.NEXT_PUBLIC_API_URL;
const envAssistantId: string | undefined = process.env.NEXT_PUBLIC_ASSISTANT_ID;
// Pass env vars as defaultValue
const [apiUrl] = useQueryState("apiUrl", {
defaultValue: envApiUrl || "",
});
const [assistantId] = useQueryState("assistantId", {
defaultValue: envAssistantId || "",
});
const [threadId] = useQueryState("threadId");
// ... rest of the implementation
}
Changes Required
- Read
process.env.NEXT_PUBLIC_API_URL and process.env.NEXT_PUBLIC_ASSISTANT_ID
- Pass env vars as
defaultValue options to useQueryState
- Ensure backward compatibility (query parameters should still override env vars)
Benefits
- ✅ Consistent with StreamProvider behavior
- ✅ Follows Next.js conventions for environment variables
- ✅ Backward compatible (query parameters still work)
- ✅ Minimal code change (6 lines)
- ✅ No breaking changes
Testing
Test Case 1: Environment Variables Only
# .env.local
NEXT_PUBLIC_API_URL=http://localhost:8383/api/v1/agent-protocol
NEXT_PUBLIC_ASSISTANT_ID=my-assistant
URL: http://localhost:3000/chat
Expected: Thread History loads ✅
Current: Thread History empty ❌
Test Case 2: Query Parameters (Backward Compatibility)
URL: http://localhost:3000/chat?apiUrl=http://localhost:8383/api/v1/agent-protocol&assistantId=my-assistant
Expected: Thread History loads ✅
Current: Thread History loads ✅
Test Case 3: Query Parameters Override Environment Variables
# .env.local
NEXT_PUBLIC_API_URL=http://default-api.example.com
NEXT_PUBLIC_ASSISTANT_ID=default-assistant
URL: http://localhost:3000/chat?apiUrl=http://override-api.example.com&assistantId=override-assistant
Expected: Uses query parameter values (not env vars) ✅
Current: N/A (no env var support) ❌
Related Issues
- None found (please link if this is a duplicate)
Additional Context
This inconsistency was discovered while integrating the Agent Chat UI with a backend API. The StreamProvider correctly loads and displays messages, but the ThreadProvider fails to load thread history, causing a confusing user experience where some features work and others don't.
The fix is straightforward and mirrors the existing pattern in StreamProvider, ensuring consistent behavior across the application.
Checklist
References
Description
The
ThreadProvidercomponent does not readNEXT_PUBLIC_API_URLandNEXT_PUBLIC_ASSISTANT_IDenvironment variables, whileStreamProviderdoes. This inconsistency causes the Thread History panel to remain empty when the application is accessed without explicit query parameters in the URL.Environment
mainbranch (as of latest commit)Steps to Reproduce
Set environment variables in
.env.local:Start the development server:
Access the application WITHOUT query parameters:
Observe the Thread History panel (left sidebar)
Expected Behavior
This is the standard Next.js pattern for configuration:
Actual Behavior
Workaround: Manually append query parameters to the URL:
When query parameters are provided, Thread History works correctly.
Root Cause
StreamProvider (Working) ✅
File:
src/providers/Stream.tsx✅ Reads environment variables
✅ Passes them as
defaultValuetouseQueryState✅ Works with and without query parameters
ThreadProvider (Broken) ❌
File:
src/providers/Thread.tsx(lines 36-40)❌ Does NOT read environment variables
❌ No
defaultValueprovided touseQueryState❌ Only works when query parameters are explicitly provided
Impact
Users Affected
Severity
Medium - Core feature (Thread History) is broken in default configuration
Workarounds
Manual Query Parameters (user-facing):
?apiUrl=...&assistantId=...to every URLURL Rewriting (server-side):
Patch ThreadProvider (our temporary solution):
Proposed Fix
Apply the same pattern used in StreamProvider to ThreadProvider:
Changes Required
process.env.NEXT_PUBLIC_API_URLandprocess.env.NEXT_PUBLIC_ASSISTANT_IDdefaultValueoptions touseQueryStateBenefits
Testing
Test Case 1: Environment Variables Only
# .env.local NEXT_PUBLIC_API_URL=http://localhost:8383/api/v1/agent-protocol NEXT_PUBLIC_ASSISTANT_ID=my-assistantURL:
http://localhost:3000/chatExpected: Thread History loads ✅
Current: Thread History empty ❌
Test Case 2: Query Parameters (Backward Compatibility)
URL:
http://localhost:3000/chat?apiUrl=http://localhost:8383/api/v1/agent-protocol&assistantId=my-assistantExpected: Thread History loads ✅
Current: Thread History loads ✅
Test Case 3: Query Parameters Override Environment Variables
# .env.local NEXT_PUBLIC_API_URL=http://default-api.example.com NEXT_PUBLIC_ASSISTANT_ID=default-assistantURL:
http://localhost:3000/chat?apiUrl=http://override-api.example.com&assistantId=override-assistantExpected: Uses query parameter values (not env vars) ✅
Current: N/A (no env var support) ❌
Related Issues
Additional Context
This inconsistency was discovered while integrating the Agent Chat UI with a backend API. The StreamProvider correctly loads and displays messages, but the ThreadProvider fails to load thread history, causing a confusing user experience where some features work and others don't.
The fix is straightforward and mirrors the existing pattern in StreamProvider, ensuring consistent behavior across the application.
Checklist
References
src/providers/Stream.tsxsrc/providers/Thread.tsx