Composio tool auth fixes, no auth support and connected accounts selection. (#5614)

* composio fix

* empty appName handling
This commit is contained in:
chiragjagga
2026-01-12 18:48:41 +08:00
committed by GitHub
parent 649a54fd2b
commit d848baeb6b
3 changed files with 450 additions and 179 deletions
@@ -63,11 +63,11 @@ class Composio_Tools implements INode {
refresh: true
},
{
label: 'Auth Status',
name: 'authStatus',
label: 'Connected Account',
name: 'connectedAccountId',
type: 'asyncOptions',
loadMethod: 'authStatus',
placeholder: 'Connection status will appear here',
loadMethod: 'listConnections',
description: 'Select which connection to use',
refresh: true
},
{
@@ -164,7 +164,7 @@ class Composio_Tools implements INode {
]
}
},
authStatus: async (nodeData: INodeData, options?: ICommonObject): Promise<INodeOptionsValue[]> => {
listConnections: async (nodeData: INodeData, options?: ICommonObject): Promise<INodeOptionsValue[]> => {
const credentialData = await getCredentialData(nodeData.credential ?? '', options ?? {})
const composioApiKey = getCredentialParam('composioApi', credentialData, nodeData)
const appName = nodeData.inputs?.appName as string
@@ -184,20 +184,44 @@ class Composio_Tools implements INode {
{
label: 'Select an App first',
name: 'placeholder',
description: 'Select an app from the dropdown to view available actions'
description: 'Select an app from the dropdown to view available connections'
}
]
}
const toolset = new LangchainToolSet({ apiKey: composioApiKey })
const authStatus = await toolset.client.getEntity('default').getConnection({ app: appName.toLowerCase() })
return [
{
label: authStatus ? 'Connected' : 'Not Connected',
name: authStatus ? 'Connected' : 'Not Connected',
description: authStatus ? 'Selected app has an active connection' : 'Please connect the app on app.composio.dev'
}
]
const appInfo = await toolset.client.apps.get({ appKey: appName.toLowerCase() })
const requiresAuth = (appInfo as any)?.no_auth !== true
if (!requiresAuth) {
return [
{
label: 'No connection needed',
name: 'No connection needed',
description: 'This app does not require authentication'
}
]
}
const connections = await toolset.client.connectedAccounts.list({ appNames: appName.toLowerCase() })
const activeConnections = connections.items?.filter((c: any) => c.status === 'ACTIVE') || []
if (activeConnections.length === 0) {
return [
{
label: 'No connections available',
name: '',
description: 'Please connect the app on app.composio.dev first'
}
]
}
return activeConnections.map((c: any) => ({
label: c.clientUniqueUserId || c.id,
name: c.id,
description: `Created: ${new Date(c.createdAt).toLocaleDateString()}`
}))
}
}
@@ -210,7 +234,7 @@ class Composio_Tools implements INode {
if (!composioApiKey) {
nodeData.inputs = {
appName: undefined,
authStatus: '',
connectedAccountId: '',
actions: []
}
throw new Error('API Key Required')
@@ -227,7 +251,37 @@ class Composio_Tools implements INode {
}
const toolset = new LangchainToolSet({ apiKey: composioApiKey })
const tools = await toolset.getTools({ actions })
const appName = nodeData.inputs?.appName as string
if (!appName) {
throw new Error('App name is required. Please select an app.')
}
const appInfo = await toolset.client.apps.get({ appKey: appName.toLowerCase() })
const requiresAuth = (appInfo as any)?.no_auth !== true
if (!requiresAuth) {
const tools = await toolset.getTools({ actions })
return tools
}
const selectedConnectionId = nodeData.inputs?.connectedAccountId as string
if (!selectedConnectionId) {
throw new Error(`Please select a connected account for ${appName}`)
}
const activeConnection = await toolset.client.connectedAccounts.get({ connectedAccountId: selectedConnectionId })
if (!activeConnection || (activeConnection as any).status !== 'ACTIVE') {
throw new Error(
`Selected connection is no longer active for ${appName}. Please select a different connection or reconnect on app.composio.dev`
)
}
const entityId = (activeConnection as any).clientUniqueUserId || 'default'
const toolsetWithEntity = new LangchainToolSet({ apiKey: composioApiKey, entityId })
const tools = await toolsetWithEntity.getTools({ actions })
return tools
}
}
+1 -1
View File
@@ -103,7 +103,7 @@
"cheerio": "^1.0.0-rc.12",
"chromadb": "3.1.6",
"cohere-ai": "^7.7.5",
"composio-core": "^0.4.7",
"composio-core": "^0.5.39",
"couchbase": "4.4.1",
"crypto-js": "^4.1.1",
"css-what": "^6.1.0",
+379 -162
View File
File diff suppressed because one or more lines are too long