P
Postizโ€ข3mo ago
Support

Ticket: Frontend Upload Error with Cloudflare Storage Integration

@Sven Just created a ticket
Question: Frontend issue when using Cloudflare as storage provider. I'm trying to use Cloudflare as storage provider. It works fine for Avatars etc. but when trying to upload an image it doesn't work and I see this error in the Browser console: [Uppy] [17:29:51] Expected a endpoint option containing a URL, or if you are not using Companion, a custom getUploadParameters implementation.
Attempted: Switched to local, there it works without issues, but I would really prefer for the uploaded assets to be on cloudflare.
Working On: -
Take it from here @Mod ๐Ÿ”ฅ
53 Replies
Nevo David
Nevo Davidโ€ข3mo ago
Did you connect a custom domain? drop your .env
Sven
Svenโ€ข3mo ago
I'm using the R2.dev subdomain. As I said, the avatars are properly uploaded and displayed, it's just the 'manual' upload of assets where I get the error in the frontend
Nevo David
Nevo Davidโ€ข3mo ago
Yes the avatars have a diffrent way of uploading from the media uploader most likely you are getting cors errors can you drop your cors configuration from cloudflare?
Sven
Svenโ€ข3mo ago
{
"AllowedOrigins": [
"http://localhost:4200",
"https://redacted"
],
"AllowedMethods": [
"GET",
"POST",
"HEAD",
"PUT",
"DELETE"
],
"AllowedHeaders": [
"Authorization",
"x-amz-date",
"x-amz-content-sha256",
"content-type"
],
"ExposeHeaders": [
"ETag",
"Location"
],
"MaxAgeSeconds": 3600
}
]
{
"AllowedOrigins": [
"http://localhost:4200",
"https://redacted"
],
"AllowedMethods": [
"GET",
"POST",
"HEAD",
"PUT",
"DELETE"
],
"AllowedHeaders": [
"Authorization",
"x-amz-date",
"x-amz-content-sha256",
"content-type"
],
"ExposeHeaders": [
"ETag",
"Location"
],
"MaxAgeSeconds": 3600
}
]
And about the .env (or rather the environment of the docker container, as the .env get's ignored -> still have another ticket open about that). Nothing special there,
STORAGE_PROVIDER: "cloudflare"
CLOUDFLARE_ACCOUNT_ID: "..."
CLOUDFLARE_ACCESS_KEY: "..""
CLOUDFLARE_SECRET_ACCESS_KEY: "..."
CLOUDFLARE_BUCKETNAME: "postiz"
CLOUDFLARE_BUCKET_URL: "..."
CLOUDFLARE_REGION: "weur"
STORAGE_PROVIDER: "cloudflare"
CLOUDFLARE_ACCOUNT_ID: "..."
CLOUDFLARE_ACCESS_KEY: "..""
CLOUDFLARE_SECRET_ACCESS_KEY: "..."
CLOUDFLARE_BUCKETNAME: "postiz"
CLOUDFLARE_BUCKET_URL: "..."
CLOUDFLARE_REGION: "weur"
( I guess there is nothing else in there that should matter) Also Iif I would get CORS errors I shouldn't I see that in teh browser console? All I see is the error from Uppy which doesn't sound like it's related to CORS but rather something wrong with the config
Nevo David
Nevo Davidโ€ข3mo ago
Can you try in AllowedOrigins to put * instead of the current domains
Sven
Svenโ€ข3mo ago
Tried it, doesn't seem to make any difference
Nevo David
Nevo Davidโ€ข3mo ago
what error are you getting? from CloudFlare? Postiz in production uses Uppy with cloudflare it works
Sven
Svenโ€ข3mo ago
I don't get a error from Cloudflare. All I get is [Uppy] [17:29:51] Expected a endpoint option containing a URL, or if you are not using Companion, a custom getUploadParameters implementation.
Nevo David
Nevo Davidโ€ข3mo ago
in CLOUDFLARE_BUCKET_URL, did you put your custom url?
Sven
Svenโ€ข3mo ago
yeah
Nevo David
Nevo Davidโ€ข3mo ago
the r2 url
Sven
Svenโ€ข3mo ago
CLOUDFLARE_BUCKET_URL: "https://.....r2.dev"
Nevo David
Nevo Davidโ€ข3mo ago
Should be something like this:
No description
Sven
Svenโ€ข3mo ago
and that works fine, if it's wrong I wouldn't be able to see the avatars
Nevo David
Nevo Davidโ€ข3mo ago
the avatars have a different technic to upload to cloudflare
Sven
Svenโ€ข3mo ago
upload yes, but the URL to deliver the avatars is using the bucket_url
Nevo David
Nevo Davidโ€ข3mo ago
it looks like cloudflare domain has limitations with rate limiting and caching, Maybe try to connect a custom subdomain?
Sven
Svenโ€ข3mo ago
Afaik I can't just use a subdomain, I first would've to have a domain in teh Cloudflare DNS ๐Ÿ˜ฆ
Nevo David
Nevo Davidโ€ข3mo ago
I can give you a subdomain to check try to add sven.git.sn and give me your records We can test it now
Sven
Svenโ€ข3mo ago
It's Cloudflare that doesnt' allow it. It needs to manage the domain to be able to use it as a custom domain
Nevo David
Nevo Davidโ€ข3mo ago
Oh
Sven
Svenโ€ข3mo ago
No description
Sven
Svenโ€ข3mo ago
Was a bit surprised by that too
Nevo David
Nevo Davidโ€ข3mo ago
I honestly don't know what is the error local uploading is not good for you?
Sven
Svenโ€ข3mo ago
yeah, it's running in a VM/Docker and I would rather not using the disk on there to store data If there is no other way then sure, I'll do it, but I would prefer not to if possible. So had a look without the container, got the repo set everything up to get it running and I'm seeing the same issue Good thing is that I now also have the sourcemaps and can actually see whats going on in the frontend JS ๐Ÿ˜‰ @Nevo David So I'm one step further, as teh error indicated I can fix that error by actually setting a endpoint (in libraries\react-shared-libraries\src\helpers\uppy.upload.ts line:26). Now the question becomes what the correct endpoint is ๐Ÿ˜‰ (maybe it's not needed, but as uppy complains that it's not that it's either that or something else is setup wrong for uppy) I guess it's supposed to go the presigned route, but for some reason it ends up somewhere were uppy requires the endpoint (which should not be needed for presigned) @Nevo David Found the actual issue. And it's really a issue in the code. The problem is that it's setup to do teh presigning for multipart uploads. Uppy by default handles only files with a size of <= 100MiB as multipart, smaller files are send as a single chunk. So one possible fix is just adding shouldUseMultipart(file : any) { return true; }, to the uppy options. (uppy.upload.ts) to handle all files as multipart. (and this does indeed fixes the issue for me). Obviously would be better to handle smaller files properly (implement the getUploadParameters callback).
Sven
Svenโ€ข3mo ago
So ended up implementing the getUploadParameters callback, it 'works'... uploads work fine, but they don't appear in Postiz. Any ideas why would be appreciated (the frontend callbacks uppy2.on('complete' ... and uppy2.on('upload-success'.... are executed and data seem ok) If you want to check what I've done so far: https://github.com/gitroomhq/postiz-app/compare/main...SvenRH:postiz-app:fix-cloudflare
GitHub
Comparing gitroomhq:main...SvenRH:fix-cloudflare ยท gitroomhq/postiz...
๐Ÿ“จ Schedule social media posts, measure them, exchange with other members and get a lot of help from AI ๐Ÿš€ - Comparing gitroomhq:main...SvenRH:fix-cloudflare ยท gitroomhq/postiz-app
Sven
Svenโ€ข3mo ago
And another update on that, just noticed that it saves it to the media server on 'complete-multipart-upload', which isn't called for singlepart uploads (and there seems to be no such callback for singlepart uploads) So there probably needs to be another endpoint for finishing the singlepart files that needs to be called by the frontend (probably from uppy2.on('upload-success'...) At this point the question becomes if it's worth even handling singlepart uploads or just just always force multipart to keep things simple
Sven
Svenโ€ข3mo ago
Also here a version with the simpler version that enables multipart uploads for all files https://github.com/SvenRH/postiz-app/tree/fix-coudflare-altnernate
GitHub
GitHub - SvenRH/postiz-app at fix-coudflare-altnernate
๐Ÿ“จ Schedule social media posts, measure them, exchange with other members and get a lot of help from AI ๐Ÿš€ - GitHub - SvenRH/postiz-app at fix-coudflare-altnernate
Nevo David
Nevo Davidโ€ข3mo ago
This one works for you in production?
Sven
Svenโ€ข3mo ago
It did yesterday in dev. ๐Ÿ˜‰ As I said earlier, taht is a bit more a 'hack' than implementing dingleparts uploads properly, but it's an easy fix
Nevo David
Nevo Davidโ€ข3mo ago
Can you make a pull request?
Sven
Svenโ€ข3mo ago
Sure, was just waiting for your feedback (if you want the simple solution or the more 'correct' one)
Nevo David
Nevo Davidโ€ข3mo ago
Can you elborate why this one works for you and without the multi-part it doesn't work for you?
Sven
Svenโ€ข3mo ago
sure. When not using multipart the upload works different. Uppy doesnt' do all the multipart upload callbacks arent' used (createMultipartUpload etc.). In this case it tries to use he getUploadParameters callback (which is not defined) and as this doesn't exist it will try to use the endpoint (so sending via a server). So the two possible solutions ended up being 1. send everythign as multipart 2. implement getUploadParameters
Nevo David
Nevo Davidโ€ข3mo ago
I don't mind converting it to multi-part, but just interesting So how does it work in production?
Sven
Svenโ€ข3mo ago
You should be able to tset it yourself. When you try to upload a file smaller tahn 100MB it will try to upload singlepart and that fails
Nevo David
Nevo Davidโ€ข3mo ago
(on platform.postiz.com)
Sven
Svenโ€ข3mo ago
no idea. I can only go by what I see and what teh documentation of uppy says should happen.
Nevo David
Nevo Davidโ€ข3mo ago
Can you create a PR so I can check it? ๐Ÿ™‚
Sven
Svenโ€ข3mo ago
give me a few minutes, just wanted to check locally again and messed up something with my environment PR has been created
Nevo David
Nevo Davidโ€ข3mo ago
Cool, will check it soon ๐Ÿ™‚ Do you know why uupy suggest to use multipart for files higher than 100mb? What's the logic behind it? less calls?
Sven
Svenโ€ข3mo ago
Yeah, multipart requires more calls. each part (I think they are each 5MB) needs to be presigned so causing a lot more calls. With single chunk there is only on presigning needed.
Nevo David
Nevo Davidโ€ข3mo ago
@xcons I know you are on a small vacation, but I don't have any knowledge about the PROs and CONs happy if you can get a look at this also
Sven
Svenโ€ข3mo ago
You can look at https://github.com/gitroomhq/postiz-app/compare/main...SvenRH:postiz-app:fix-cloudflare you can see that I implemented the presigning for single chunk uploads. Just the beavour when the upload is finished is not done there (so the added file is never added to postiz)
GitHub
Comparing gitroomhq:main...SvenRH:fix-cloudflare ยท gitroomhq/postiz...
๐Ÿ“จ Schedule social media posts, measure them, exchange with other members and get a lot of help from AI ๐Ÿš€ - Comparing gitroomhq:main...SvenRH:fix-cloudflare ยท gitroomhq/postiz-app
Sven
Svenโ€ข3mo ago
I would've finished it, but that would require a bit more changes and raises the question if the handling for completion of multipart uploads shoudl also be changed (would make senes to keep it consistent)
Sven
Svenโ€ข3mo ago
And about pros/cons. The Uppy docs (https://uppy.io/docs/aws-s3/) have a nice summary of it:
Multipart uploads start to become valuable for larger files (100 MiB+) as it uploads a single object as a set of parts. This has certain benefits, such as improved throughput (uploading parts in parallel) and quick recovery from network issues (only the failed parts need to be retried). The downside is request overhead, as it needs to do creation, signing (unless you are signing on the client), and completion requests besides the upload requests. For example, if you are uploading files that are only a couple kilobytes with a 100ms roundtrip latency, you are spending 400ms on overhead and only a few milliseconds on uploading.
Uppy
Sleek, modular open source JavaScript file uploader
Sven
Svenโ€ข3mo ago
Small update. Noticed that the change caused a type error when building a docker container. Fixed the issue and it compiles fine now.
Nevo David
Nevo Davidโ€ข3mo ago
Will this effect only cloudflare, or also local uploading?
Sven
Svenโ€ข3mo ago
only cloudflare @Nevo David you may have alraedy noticed, someone else tested my fix and it fixed cloudflare for them (https://discord.com/channels/1243410146097500202/1296546635245158442)
Nevo David
Nevo Davidโ€ข3mo ago
Yup, will merge it soon
xcons
xconsโ€ข2mo ago
I see it got merged while waiting for me on feedback - https://github.com/gitroomhq/postiz-app/pull/373/files - but yeah, generally I would have said this was fine.
Sven
Svenโ€ข2mo ago
@xcons in case you haven't read everything. I also started implementing it 'properly' (making singlepart uploads work), but that requires additional changes to handle when the upload has finished which I haven't done (didn't want to make a lot of additonal changes).
xcons
xconsโ€ข2mo ago
@Sven No worries, are you still working on this out of interest?
Want results from more Discord servers?
Add your server