Skip to content

Commit 917e02e

Browse files
Remove user supplied values from responses (#5780)
1 parent c22f2d3 commit 917e02e

5 files changed

Lines changed: 28 additions & 14 deletions

File tree

packages/server/src/controllers/chat-messages/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -168,7 +168,7 @@ const removeAllChatMessages = async (req: Request, res: Response, next: NextFunc
168168
const chatflowid = req.params.id
169169
const chatflow = await chatflowsService.getChatflowById(req.params.id, workspaceId)
170170
if (!chatflow) {
171-
return res.status(404).send(`Chatflow ${req.params.id} not found`)
171+
return res.status(404).send('Chatflow not found')
172172
}
173173
const flowData = chatflow.flowData
174174
const parsedFlowData: IReactFlowObject = JSON.parse(flowData)

packages/server/src/controllers/chatflows/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,7 @@ const updateChatflow = async (req: Request, res: Response, next: NextFunction) =
181181
}
182182
const chatflow = await chatflowsService.getChatflowById(req.params.id, workspaceId)
183183
if (!chatflow) {
184-
return res.status(404).send(`Chatflow ${req.params.id} not found`)
184+
return res.status(404).send('Chatflow not found')
185185
}
186186
const orgId = req.user?.activeOrganizationId
187187
if (!orgId) {

packages/server/src/controllers/nvidia-nim/index.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ const pullImage = async (req: Request, res: Response, next: NextFunction) => {
4545
const imageTag = req.body.imageTag
4646
const apiKey = req.body.apiKey
4747
await NimContainerManager.pullImage(imageTag, apiKey)
48-
return res.send(`Pulling image ${imageTag}`)
48+
return res.send('Pulling image')
4949
} catch (error) {
5050
next(error)
5151
}
@@ -62,7 +62,7 @@ const startContainer = async (req: Request, res: Response, next: NextFunction) =
6262
return res.status(400).send('nimRelaxMemConstraints must be 0 or 1')
6363
}
6464
await NimContainerManager.startContainer(imageTag, apiKey, hostPort, nimRelaxMemConstraints)
65-
return res.send(`Starting container ${imageTag}`)
65+
return res.send('Starting container')
6666
} catch (error) {
6767
next(error)
6868
}
@@ -74,7 +74,7 @@ const getImage = async (req: Request, res: Response, next: NextFunction) => {
7474
const images = await NimContainerManager.userImageLibrary()
7575
const image = images.find((img: any) => img.tag === imageTag)
7676
if (!image) {
77-
return res.status(404).send(`Image ${imageTag} not found`)
77+
return res.status(404).send('Image not found')
7878
}
7979
return res.json(image)
8080
} catch (error) {
@@ -91,7 +91,7 @@ const getContainer = async (req: Request, res: Response, next: NextFunction) =>
9191
const images = await NimContainerManager.userImageLibrary()
9292
const image = images.find((img: any) => img.tag === imageTag)
9393
if (!image) {
94-
return res.status(404).send(`Image ${imageTag} not found`)
94+
return res.status(404).send('Image not found')
9595
}
9696

9797
const containers = await NimContainerManager.listRunningContainers()
@@ -103,14 +103,14 @@ const getContainer = async (req: Request, res: Response, next: NextFunction) =>
103103
return res.json(portInUse)
104104
} else {
105105
return res.status(409).send({
106-
message: `Port ${port} is already in use by another container`,
106+
message: 'Port is already in use by another container',
107107
container: portInUse
108108
})
109109
}
110110
}
111111

112112
// If no container found with matching port, return 404
113-
return res.status(404).send(`Container of ${imageTag} with port ${port} not found`)
113+
return res.status(404).send('Container not found')
114114
} catch (error) {
115115
next(error)
116116
}

packages/server/src/controllers/variables/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -88,7 +88,7 @@ const updateVariable = async (req: Request, res: Response, next: NextFunction) =
8888
}
8989
const variable = await variablesService.getVariableById(req.params.id, workspaceId)
9090
if (!variable) {
91-
return res.status(404).send(`Variable ${req.params.id} not found in the database`)
91+
return res.status(404).send('Variable not found in the database')
9292
}
9393
const body = req.body
9494
const updatedVariable = new Variable()

packages/server/src/routes/oauth2/templates.ts

Lines changed: 19 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,13 @@
55
* The templates provide consistent styling and behavior for success and error pages.
66
*/
77

8+
/**
9+
* Escapes HTML special characters to prevent XSS attacks
10+
*/
11+
const escapeHtml = (unsafe: string): string => {
12+
return unsafe.replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/"/g, '&quot;').replace(/'/g, '&#039;')
13+
}
14+
815
export interface OAuth2PageOptions {
916
title: string
1017
statusIcon: string
@@ -20,11 +27,18 @@ export interface OAuth2PageOptions {
2027
export const generateOAuth2ResponsePage = (options: OAuth2PageOptions): string => {
2128
const { title, statusIcon, statusText, statusColor, message, details, postMessageType, postMessageData, autoCloseDelay } = options
2229

30+
// Escape all user-controlled content to prevent XSS
31+
const safeTitle = escapeHtml(title)
32+
const safeStatusIcon = escapeHtml(statusIcon)
33+
const safeStatusText = escapeHtml(statusText)
34+
const safeMessage = escapeHtml(message)
35+
const safeDetails = details ? escapeHtml(details) : undefined
36+
2337
return `
2438
<!DOCTYPE html>
2539
<html>
2640
<head>
27-
<title>${title}</title>
41+
<title>${safeTitle}</title>
2842
<style>
2943
body {
3044
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
@@ -65,9 +79,9 @@ export const generateOAuth2ResponsePage = (options: OAuth2PageOptions): string =
6579
</head>
6680
<body>
6781
<div class="container">
68-
<div class="status">${statusIcon} ${statusText}</div>
69-
<div class="message">${message}</div>
70-
${details ? `<div class="details">${details}</div>` : ''}
82+
<div class="status">${safeStatusIcon} ${safeStatusText}</div>
83+
<div class="message">${safeMessage}</div>
84+
${safeDetails ? `<div class="details">${safeDetails}</div>` : ''}
7185
</div>
7286
<script>
7387
// Notify parent window
@@ -81,7 +95,7 @@ export const generateOAuth2ResponsePage = (options: OAuth2PageOptions): string =
8195
} catch (error) {
8296
console.log('Could not notify parent window:', error);
8397
}
84-
98+
8599
// Close window after delay
86100
setTimeout(function() {
87101
window.close();

0 commit comments

Comments
 (0)