Azure-functions-host: Out of proc languages stream support

Created on 3 Apr 2017  ยท  27Comments  ยท  Source: Azure/azure-functions-host

For all Node.js bindings (trigger/input/output) streaming is not supported - the data is put into an in memory buffer first. This can cause out of memory issues for people attempting to process large blobs for example.

We should investigate ways to support a streaming model, as you can optionally do in C# (by binding to a Stream). E.g. we might have a binding hint that allows the function to request a stream, and we provide the user code with a stream over the underlying SDK stream.

Note that if we move out of process for languages, streaming is complicated. We need to consider this when making any new programming model decisions.

language-extensibility lang-js needs-investigation languages

Most helpful comment

Update?

All 27 comments

This will also alow realistic static web serving of file based resources like HTML, css images etc.

I'd love to see this.

node without streams? really?

Agree this should be a v high priority for js/ts to have 1st class support

@goofballLogic Yep :-). Based on my interactions it seems like there isn't a very large base of people using NodeJS with Azure Functions (Its at least seems to always be the same 5-6 names on any GitHub ticket). Given the small number of people, the product group is doing an amazing job working through issues annyway. Its gotten a TON better in the last ~year. With that said, some silly things like this seem to take time.

If I had noticed https://github.com/lambci/lambci earlier I probably would have stuck with AWS Lambda. The big thing I was missing on the Lambda side was CI/CD and I didn't want to pay for another service to get it. However, at this point things work well enough, and especially with the larger file support that Azure Functions handles vs. Lambda it makes several things I'm doing a lot easier.

Add in the streaming support, however; and the larger file support would be an even bigger reason to choose Azure Functions.

Azure Functions has the potential to be an amazing offering for NodeJS CI/CD function development. Its getting there, but isn't quite 100% there yet.

Yeah we're evaluating AWS vs Azure for a hybrid C# / node.js serverless implementation. Had assumed that Azure would be the way to go, but I think it's not quite up to the job yet : (

โฃSent from TypeApp โ€‹

On 10 Aug 2017, 13:39, at 13:39, Doug Logan notifications@github.com wrote:

@goofballLogic Yep :-). Based on my interactions it seems like there
isn't a very large base of people using NodeJS with Azure Functions
(Its at least seems to always be the same 5-6 names on any GitHub
ticket). Given the small number of people, the product group is doing
an amazing job working through issues annyway. Its gotten a TON better
in the last ~year. With that said, some silly things like this seem to
take time.

If I had noticed https://github.com/lambci/lambci earlier I probably
would have stuck with AWS Lambda. The big thing I was missing on the
Lambda side was CI/CD and I didn't want to pay for another service to
get it. However, at this point things work well enough, and especially
with the larger file support that Azure Functions handles vs. Lambda it
makes several things I'm doing a lot easier.

Add in the streaming support, however; and the larger file support
would be an even bigger reason to choose Azure Functions.

Azure Functions has the potential to be an amazing offering for NodeJS
CI/CD function development. Its getting there, but isn't quite 100%
there yet.

--
You are receiving this because you were mentioned.
Reply to this email directly or view it on GitHub:
https://github.com/Azure/azure-webjobs-sdk-script/issues/1361#issuecomment-321539230

@goofballLogic It all depends what you're doing. If you're dealing with small files, then Lambda is probably faster / more consistent, etc. However, take a close look at these Lambda limits:
http://docs.aws.amazon.com/lambda/latest/dg/limits.html

One of our projects was uploading/processing a ~6.5MB XML file. Lambda couldn't handle that. I'd say that's even more core than streaming. This is kind of what happens when you're bleeding edge I guess.

I would say in general Lambda still seems more polished than Azure Functions, but that gap is quickly closing and even Lambda has its stupid stuff (e.g. File Limits).

Now there are ways around this in Lambda. You can write to S3 instead of the Lambda function, then retrieve the file from the Lambda Function and process it. However, this is a LOT more code than just handling the request.

With both platforms being pretty horrible to debug once deployed, more code = more trouble. As a result with any Servlerless stack it is definitely a place where the KISS principal applies.

@goofballLogic I should mention, things got a lot faster and more reliable with NodeJS on Azure when I WebPacked things into their own orphaned git branch (See https://github.com/securityvoid/pack-git ). If you play with Azure much you should check it out.

I decided not to clutter up my main repo with build artifacts. I ws also thinking that every function will have a full coppy of all it's deps in it's bundle file. The storage is limited, but at least we don't pay for it ;)

Is there any update on this request? Would love to be able to stream files

This lack of support kinda makes the blob storage service unfeasible for node projects, would love to see this implemented.

Can someone clarify - there is still no way to serve a binary file from Azure Function using Node?

Would really like this functionality in the node stack. Having to pull a blob into memory seems like a big miss.

Is there any update on this?

Update?

any update on this? I am trying to achieve the exact same thing to stream the the Blob.

any update?
Stream is very important at FaaS. it's limited on memory & storage...

any update on this topic? I guess the possibility for streaming Azure storage blobs via Azure functions to a SPA is a nice pattern for many applications.

Has anyone found any way to serve files in NodeJS? Even if I return a binary file as a string or buffer, it doesn't seem to work, the file is unreadable and the encoding looks off.

@jacks0n Are you utilizing "isRaw": true in your response object? That tells the Azure Function to not to do any of its mangling / auto-handling of the response.

Beyond that, my answer my help here:
https://stackoverflow.com/questions/43810082/azure-functions-nodejs-response-body-as-a-stream

I haven't had any problem serving up static files. It just doesn't handle huge files very well.

@securityvoid yes I'm using "isRaw": true in my response object. I found converting the response body (which is a zip file buffer) with new Uint8Array(body) did the trick.

Adding streams to Node based functions would be great. In the mean time is there a way to catch the error and respond to the user agent? Testing using core tools failures start around 25MB of data, and postman hangs waiting for a response from the server. If I could send the user agent a 4xx response instead of crashing the app that would be helpful.

With Azure releasing a JAM stack product based on Functions this issue is going to present a big friction to adoption imo for both performance and capability reasons (avoiding OOM). I was excited for Static Web Apps until I saw this limitation still exists.

Would love for this to be prioritised.

3 years old too!

Hard to believe that this is going to force me to learn C#... But it is.

How in the world is this not a priority?

Edit: I was looking to have a file downloaded from blob storage so I definitely needed streaming, but I circumvented it by redirecting to the blob storage directly and generating a short-lived SAS token that applies only to that specific resource. Code snippet below for those in the same situation. Ultimately I'm happier with this solution anyway.

const path = context.bindingData.resourceId;

/*
    I've removed the logic where I check if the authenticated user should be allowed access to this specific resource.
*/

const blobSAS = generateBlobSASQueryParameters({
    containerName: process.env.DOCUMENTS_CONTAINER_NAME, // Required
    blobName: path, // Required
    permissions: BlobSASPermissions.parse("r"), // Required
    startsOn: new Date(), // Required
    expiresOn: new Date(new Date().valueOf() + 30000) // Optional. Date type
   }, new StorageSharedKeyCredential(process.env.ACCOUNT_NAME, process.env.ACCOUNT_KEY)
).toString();

context.res = {
    status: 301,
    headers: {
        "Location": `https://${process.env.ACCOUNT_NAME}.blob.core.windows.net/${process.env.DOCUMENTS_CONTAINER_NAME}/${path}?${blobSAS}`
    }
}
Was this page helpful?
0 / 5 - 0 ratings

Related issues

helgemahrt picture helgemahrt  ยท  4Comments

justinyoo picture justinyoo  ยท  3Comments

ahmelsayed picture ahmelsayed  ยท  4Comments

ladeak picture ladeak  ยท  3Comments

mathewc picture mathewc  ยท  4Comments