Binary Data not passing through

Hi, hoping this is a quick fix…

Describe the problem/error/question

I’m trying to strip out .pdf attachments from GMail, and upload them to GDrive. I’m doing some checks for a folder ID first to file the attachments in the correct folder in GDrive (so the folders are years - 2023, 2024, 2025 - I’m pulling the year from the attachment and searching for that folder in google drive and if it doesn’t exist I’m creating it.)

When I get to the Google Drive Upload node its complaining that the binary doesn’t have any data in it, even though its there in the input. So I’m bringing that binary data forward with a merge node - so its right in front of the Google Drive upload node. Merging it with the folder ID I found on the search.

What is the error message (if any)?

If I dont merge - it complains that there is no binary data. If I do merge its getting stuck on the Input Data Field:

{{ $(‘Merge Binary Data Forward’).item.binary.keys() }}

Saying that it can’t use .keys() on undefined data… which is the folder ID data as it only has the ID field, not the rest of the json info that the attachments have.

Which is annoying as I’m specifying .binary which the folder ID isn’t… so I’m not sure why its even showing up in the binary.keys() call.

Please share your workflow

Share the output returned by the last node

Error Debug:
{
“errorMessage”: “keys can’t be used on undefined value”,
“errorDescription”: “To ignore this error, add a ? to the variable before this function, e.g. my_var?.keys”,
“errorDetails”: {},
“n8nDetails”: {
“parameter”: “inputDataFieldName”,
“time”: “2/20/2025, 10:27:23 AM”,
“n8nVersion”: “1.78.1 (Cloud)”,
“binaryDataMode”: “filesystem”,
“stackTrace”: [
“ExpressionExtensionError: keys can’t be used on undefined value”,
" at checkIfValueDefinedOrThrow (/usr/local/lib/node_modules/n8n/node_modules/n8n-workflow/dist/Extensions/utils.js:26:15)“,
" at Proxy.extend (/usr/local/lib/node_modules/n8n/node_modules/n8n-workflow/dist/Extensions/ExpressionExtension.js:294:48)”,
" at Proxy.eval (eval at getFunction (/usr/local/lib/node_modules/n8n/node_modules/@n8n/tournament/dist/FunctionEvaluator.js:14:22), :6:47)“,
" at FunctionEvaluator.evaluate (/usr/local/lib/node_modules/n8n/node_modules/@n8n/tournament/dist/FunctionEvaluator.js:20:19)”,
" at Tournament.execute (/usr/local/lib/node_modules/n8n/node_modules/@n8n/tournament/dist/index.js:43:31)“,
" at evaluateExpression (/usr/local/lib/node_modules/n8n/node_modules/n8n-workflow/dist/ExpressionEvaluatorProxy.js:123:16)”,
" at Expression.renderExpression (/usr/local/lib/node_modules/n8n/node_modules/n8n-workflow/dist/Expression.js:238:70)“,
" at Expression.resolveSimpleParameterValue (/usr/local/lib/node_modules/n8n/node_modules/n8n-workflow/dist/Expression.js:217:34)”,
" at Expression.getParameterValue (/usr/local/lib/node_modules/n8n/node_modules/n8n-workflow/dist/Expression.js:300:25)“,
" at ExecuteContext._getNodeParameter (/usr/local/lib/node_modules/n8n/node_modules/n8n-core/dist/execution-engine/node-execution-context/node-execution-context.js:203:46)”,
" at ExecuteContext.getNodeParameter (/usr/local/lib/node_modules/n8n/node_modules/n8n-core/dist/execution-engine/node-execution-context/execute-context.js:30:93)“,
" at ExecuteContext.execute (/usr/local/lib/node_modules/n8n/node_modules/n8n-nodes-base/dist/nodes/Google/Drive/v2/actions/file/upload.operation.js:65:37)”,
" at ExecuteContext.router (/usr/local/lib/node_modules/n8n/node_modules/n8n-nodes-base/dist/nodes/Google/Drive/v2/actions/router.js:58:83)“,
" at processTicksAndRejections (node:internal/process/task_queues:95:5)”,
" at ExecuteContext.execute (/usr/local/lib/node_modules/n8n/node_modules/n8n-nodes-base/dist/nodes/Google/Drive/v2/GoogleDriveV2.node.js:16:16)“,
" at WorkflowExecute.runNode (/usr/local/lib/node_modules/n8n/node_modules/n8n-core/dist/execution-engine/workflow-execute.js:633:19)”,
" at /usr/local/lib/node_modules/n8n/node_modules/n8n-core/dist/execution-engine/workflow-execute.js:882:51",
" at /usr/local/lib/node_modules/n8n/node_modules/n8n-core/dist/execution-engine/workflow-execute.js:1216:20"
]
}
}

Information on your n8n setup

n8n Version 1.78.1

Source Code GitHub - n8n-io/n8n: Fair-code workflow automation platform with native AI capabilities. Combine visual building with custom code, self-host or cloud, 400+ integrations.

License Sustainable Use License + n8n Enterprise License

Instance ID 3955e6b8dd3adb97f8a92645d18fbfdb3d582abc3447e024c718f15c4d08b59f

Running on the Windows 10 Pro
n8n Cloud on Chrome

To start (maybe this is the only issue), you probably just want data (literally just that word) as a fixed value in your upload node’s Input Data Field Name. You have an expression {{ $('Merge Binary Data Forward1').item.binary.keys()}} which would probably resolve to an array of field names (like [“fileName”,“type”,…], not the name of the binary item (which is probably literally named “data”) that you want to upload.

Try changing that and if you’re still having troubles, we’ll go round 2.

Thanks for your help…

Okay so I tried the “data” approach and its just saying the same:

The item has no binary field ‘data’ [item 0]

I’ve stripped it right back to just the gmail and gdrive nodes now… with almost default settings, and its still saying the same.

Whats odd is that the binary tab shows the attachments there in the input… so its getting them.

Post a screenshot of what the JSON view of the output side of the Trigger node (or the input side of the upload) looks like on an execution where the trigger picked up an email containing attachments. I don’t have it set up to see what it looks like, but I suspect there are some base64 strings that would need to be extracted into binary objects before they feed into the upload.

Here you go - sorry its tiny as I zoomed out to capture the lot!

Ok. That didn’t help as much as I hoped, so I set it up to see how n8n presents it. If you switch to the Binary view on the trigger output, you’ll probably see something like this:

So your Input Data Field Name probably needs to be (literally) attachment_0 Most of the time, the name of binaries emitted from n8n nodes is data, which is why the instructions, placeholders, etc. etc. all suggest that as the name of the binary input item. IMO, this is a “learning curve” item in n8n where there’s probably some room for improvement in the UX area.

The issue with having explicitly written attachment names is that I have more than one attachment - so I’m not sure how to upload more than one.

I can use this syntax:

{{ $binary.keys()[0] }}

And it resolves to ‘attachment_0’ and uploads correctly… but I need to pass the entire list, not just a single element.

Any other approach you can think of? Weirdly I had this working before for just simple multiple uploads, but it now doesn’t work. My problems started when my workflow got more complicated and tried to get clever with folder name searching and creation… now the simple file upload doesn’t even work. Really bizarre.

Thanks again

Found this workflow example that seems to do the trick… need to investigate further, but initial test worked:

Code nodes have to set up a sandbox to run, which can slow things down, so you might prefer to use a Split Out node. The “secret” to making this work is to specify $binary (again, that’s the “fixed”, literal value, not an expression) as the Fields to Split Out parameter value.

Then, since the name of the binary is still different in each split out item/object, reference the name of it (e.g. in the Upload node’s Input Data Field Name) with an expression (this time not a fixed, literal value) like: {{ $binary.keys()[0] }}. Likewise, since there will only be one binary in each item/object, you can also reference attributes of the binary using index zero [0] with expressions like {{ $binary.values()[0].fileName }}, {{ $binary.values()[0].fileType }} or {{ $binary.values()[0].mimeType }}

1 Like

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.