syonip / blog-comments

0 stars 0 forks source link

flutter-video-upload-firebase-storage-hls #6

Open utterances-bot opened 4 years ago

utterances-bot commented 4 years ago

How to make a serverless Flutter video sharing app with Firebase Storage, including HLS and client-side encoding | Jonathan's Dev Blog

cover What we’re building We’ll see how to build a flutter app for iOS/Android that allows users to view and share videos. In my previous post I showed how to do this with Publitio as our video storage API. In this tutorial we’ll use Firebase Cloud Storage to host the videos…

https://www.learningsomethingnew.com/flutter-video-upload-firebase-storage-hls

Scuttman commented 4 years ago

Thanks for this. Very helpful. I am building an emergency education app in Malawi as schools are closing! Have you been able to make it work using the imagepicker.gallery rather than imagepicker.camera? I tried to select videos from my gallery but it failed to encode every time. Works find with the camera though.

syonip commented 4 years ago

Hi @Scuttman, I haven't tested it with gallery, but it should work the same. What error are you getting? My first guess would be missing storage permissions.

Scuttman commented 4 years ago

The error occurs on line 50 of the encoding_provider.dart. It seems to encode the file but then the error suggests the file cannot be found which does suggest permissions although when testing the app, it asked for permission to view gallery and let me select. I get ‘apis/encoding_provider.dart': Failed assertion: line 50 pos 12: 'rc == 0': is not true..’

It works for the encoded video from the camera. Do I need to add something to the Android Manifest file?

Thanks for your help. Have almost completed the project now so demonstrating tomorrow to the Education Ministry.

From: syonip notifications@github.com Reply-To: syonip/blog-comments reply@reply.github.com Date: Sunday, 22 March 2020 at 23:25 To: syonip/blog-comments blog-comments@noreply.github.com Cc: Chris Scutt chris@cjsconsultingservices.com, Mention mention@noreply.github.com Subject: Re: [syonip/blog-comments] flutter-video-upload-firebase-storage-hls (#6)

Hi @Scuttmanhttps://github.com/Scuttman, I haven't tested it with gallery, but it should work the same. What error are you getting? My first guess would be missing storage permissions.

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHubhttps://github.com/syonip/blog-comments/issues/6#issuecomment-602275620, or unsubscribehttps://github.com/notifications/unsubscribe-auth/ACGTCQX62IOSW5JFYOU7EC3RIZ63LANCNFSM4LRKSNYQ.

syonip commented 4 years ago

OK i've tested it on my android device, it seems there's some bug with ffmpeg's ability to receive file paths that contain a space character, like where WhatsApp or Telegram save videos. That's probably the issue.

I've deployed a fix for you in a separate branch: https://github.com/syonip/flutter_fbstorage_video_upload/tree/gallery

Good luck with the Ministry!

Scuttman commented 4 years ago

Thank you so much. I will test! Your example has already been a huge help.

From: syonip notifications@github.com Reply-To: syonip/blog-comments reply@reply.github.com Date: Tuesday, 24 March 2020 at 12:35 To: syonip/blog-comments blog-comments@noreply.github.com Cc: Chris Scutt chris@cjsconsultingservices.com, Mention mention@noreply.github.com Subject: Re: [syonip/blog-comments] flutter-video-upload-firebase-storage-hls (#6)

OK i've tested it on my android device, it seems there's some bug with ffmpeg's ability to receive file paths that contain a space character, like where WhatsApp or Telegram save videos. That's probably the issue.

I've deployed a fix for you in a separate branch: https://github.com/syonip/flutter_fbstorage_video_upload/tree/gallery

Good luck with the Ministry!

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHubhttps://github.com/syonip/blog-comments/issues/6#issuecomment-603160317, or unsubscribehttps://github.com/notifications/unsubscribe-auth/ACGTCQVVF6VQY4MORM3LNVLRJCEHTANCNFSM4LRKSNYQ.

Scuttman commented 4 years ago

Syonip, another quick question if that is ok. I have my app in the Alpha testing stage now and it uploads video nicely. However, the videos appear in folders linked to the video name. I want to structure the videos by subject/topic etc but when I change the upload path, the videos encode and upload fine but won't play.

I am assuming the issue is to do with the encoding and that the encoded files cannot cope with the longer url or that although they upload in a different place, the urls inside the master file are not coping with the uploaded location and still looking at the name of the file for a local?

I am expecting to have 1000s of videos over time. This will get difficult to keep organised if I cannot use a hierarchal structure to match the curriculum. If you have time to give me a pointer on this, I would appreciate. I have tried lots of different changes to the code but end up back at the default to make it work!!! Thanks.

syonip commented 4 years ago

Hi @Scuttman , What error message are you getting? In order to check the file uploaded correctly, you can go to firebase console and open the video from the web browser, it should play.

Sylvester-dev commented 4 years ago

Hi @syonip ,It's really a nice blog but i have a doubt here that first we get video length then encode and then upload it and then display it but how can we do live streaming with it (HLS) in flutter. Is there any change we need to do or any other way to do live streaming in flutter based app.

By live streaming i mean as in instagram people come live and many others can see their live stream and message at same time so something like this.

As i can not find any source which tell about how to have feature of live streaming in flutter. Thanks.

syonip commented 4 years ago

Hi @VineetMaker, glad you liked the post :) I think what you're talking about is live streaming, which is different from serving a hosted video (VOD). For live streaming you probably need some WebRTC implementation. I haven't tried it, but take a look at agora, I think they have a flutter SDK: https://medium.com/agora-io/add-real-time-video-to-your-flutter-apps-using-the-agora-flutter-sdk-68ae6d8fa6d8

Sylvester-dev commented 4 years ago

@syonip thanks for the fast reply, Agora is used for video calling and most probably i don't think we can use it for live streaming. I got a question, can we implement this live stream feature in our website that we make and then integrate our website with flutter app so that our app can play that live stream. In app we can use video player to play that stream directly on our app. Is it possible if yes then any suggested way or an article.
Thank you.

syonip commented 4 years ago

Did you try using the video_player plugin with the stream url?

On Sun, 10 May 2020 at 14:05, VineetMaker notifications@github.com wrote:

@syonip https://github.com/syonip thanks for the fast reply, Agora is used for video calling and most probably i don't think we can use it for live streaming. I got a question, can we implement this live stream feature in our website that we make and then integrate our website with flutter app so that our app can play that live stream. In app we can use video player to play that stream directly on our app. Is it possible if yes then any suggested way or an article. Thank you.

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub https://github.com/syonip/blog-comments/issues/6#issuecomment-626310378, or unsubscribe https://github.com/notifications/unsubscribe-auth/ABJKLCJVKRWM6FMY42C2IX3RQ2C5XANCNFSM4LRKSNYQ .

Sylvester-dev commented 4 years ago

@syonip no not yet

developerfix commented 4 years ago

Can anyone help me in this,

I want user to upload only 15-20 seconds video from its phone to the app(same functionality like tiktok). I am using the above code. can i restrict that only 15-20 seconds video should be uploaded?

Kindly please help...

syonip commented 4 years ago

Hi @developerfix , Notice in setState there's a calculation of the video duration: _videoDuration = EncodingProvider.getDuration(info); You could simply add some logic there to prevent upload of long videos. Good luck :)

bsurji commented 4 years ago

Dear @syonip,

Thank you for this great tutorial. I am having an issue when uploading the file. When choosing the video to upload it compresses it but after compressing it nothing happens and it gives me the following output: flutter: Loading flutter-ffmpeg. Loaded mobile-ffmpeg-min-gpl-x86_64-4.3.1-lts-20200125 flutter: Loaded flutter-ffmpeg-ios-x86_64. Getting media information for /Users/bsurji/Library/Developer/CoreSimulator/Devices/A4E5A86C-7B29-4F7B-A6D8-A3DBEC9F4B14/data/Containers/Data/Application/7E036A51-7909-4DB1-B0A6-731E2DD704E1/Documents/Videos/video8904/copy.mp4. flutter: Input #0, mov,mp4,m4a,3gp,3g2,mj2, from '/Users/bsurji/Library/Developer/CoreSimulator/Devices/A4E5A86C-7B29-4F7B-A6D8-A3DBEC9F4B14/data/Containers/Data/Application/7E036A51-7909-4DB1-B0A6-731E2DD704E1/Documents/Videos/video8904/copy.mp4': flutter: Metadata: flutter: major_brand : flutter: qt flutter: flutter: minor_version : flutter: 0 flutter: flutter: compatible_brands: flutter: qt flutter: flutter: creation_time : flutter: 2020-06-14T15:09:16.000000Z flutter: flutter: Duration: flutter: 00:00:55.90 flutter: , start: flutter: 0.000000 flutter: , bitrate: flutter: 973 kb/s flutter: flutter: Stream #0:0 flutter: (und) flutter: : Audio: aac (mp4a / 0x6134706D), 48000 Hz, stereo, fltp, 185 kb/s flutter: (default) flutter: flutter: Metadata: flutter: creation_time : flutter: 2020-06-14T15:09:16.000000Z flutter: flutter: handler_name : flutter: Core Media Audio flutter: flutter: Stream #0:1 flutter: (und) flutter: : Video: h264 (avc1 / 0x31637661), yuv420p(tv, bt709), 1164x1280 [SAR 1:1 DAR 291:320], 782 kb/s flutter: , flutter: 14.58 fps, flutter: 30 tbr, flutter: 30k tbn, flutter: 60k tbc flutter: (default) flutter: flutter: Metadata: flutter: creation_time : flutter: 2020-06-14T15:09:16.000000Z flutter: flutter: handler_name : flutter: Core Media Video flutter: flutter: encoder : flutter: H.264 flutter: flutter: NoSuchMethodError: The method '/' was called on null. Receiver: null Tried calling: /(null)

If you could advise me on what to do I would really appreciate it.

Kind Regards,

tunthey commented 4 years ago

Thank you so much for this amazing tutorial, I was able to use and adapt it into my application. However I am having problem viewing the uploaded video and couldn't figure out why.

Here is the error that video player is reporting:

E/flutter (32430): [ERROR:flutter/lib/ui/ui_dart_state.cc(157)] Unhandled Exception: PlatformException(VideoError, Video player had error com.google.android.exoplayer2.ExoPlaybackException: com.google.android.exoplayer2.upstream.HttpDataSource$InvalidResponseCodeException: Response code: 400, null)

I can deduct that it is a 400 bad request error, this is the url that it is trying to open

https://firebasestorage.googleapis.com/v0/b/pheemee-6a1e7.appspot.com/o/video%2F3869%2Fmaster.m3u8?alt=media&token=0e329676-680a-4808-b81b-a2941afd57b7

I used my browser to open it and it open just fine so I don't understand why a Response code 400 is being returned.

I will really appreciate your help.

Thanks

tunthey commented 4 years ago

Don't worry, I figured out what the problem was, I added "/" to the videoURL during my attempt to organize the videos into a single folder in my firebase storage.

syonip commented 4 years ago

Hi @bsurji, Are you getting this error when running the code from the example on github? If not, try running the example and see if you still get an error. https://github.com/syonip/flutter_fbstorage_video_upload

syonip commented 4 years ago

Thanks @tunthey , Glad you solved it :)

bsurji commented 4 years ago

@syonip

I tested it on an Android Simulator when downloading an MP4 video online and uploading it uploads fine but when uploading a video in the gallery recorded from the phone the video uploads but the VideoURL goes blank and outputs the following error:

I/flutter (22003): Too many packets buffered for output stream 0:1. I/flutter (22003): Conversion failed! I/flutter (22003): 'package:elepho/models/encoder_provider.dart': Failed assertion: line 32 pos 12: 'rc == 0': is not true.

When running it on an ios simulator it does nothing after the video finishes compressing and gives me the error I posted previously:

flutter: NoSuchMethodError: The method '/' was called on null. Receiver: null Tried calling: /(null)

If you could support me in this matter I would highly appreciate it.

Kind Regards,

syonip commented 4 years ago

Hi @bsurji , Could you open an issue in the repository? https://github.com/syonip/flutter_fbstorage_video_upload

aytunch commented 3 years ago

@syonip Hi thanks for this gem of an article. I want to know how we can carry the ffmpeg encoding process to cloud functions? Is there a easy library which does ffmpeg hls encoding in cloud functions or in another google cloud product? I think these backend can use python language as well. We will send the high res original video and the cloud function will make all the lower quality versions + calculate video duration + generate several thumbnails + upload to firebase storage. I want my client to be as light as possible. And I hope you can one day cover the topic of live streaming in the future. Take care.

syonip commented 3 years ago

Thanks @aytunch ! About cloud encoding, there are definitely products that can do that, like AWS elastic transcoder, Publitio (which I wrote about in a previous post), Cloudinary and more. You'd need to upload the video to firebase storage, and have a cloud function that would then upload it to an external API. I would be careful trying to run the actual encoding in a cloud function, as they have a hard limit of 9 minutes I think. Also, I think you can't escape some preliminary encoding on the client before uploading, as the raw HD videos taken on an iPhone can be huge, and can kill your upload quota.

cbawebdesign commented 3 years ago

hello! i am trying to run the example and keep getting : parse error on the mobile device

syonip commented 3 years ago

Hi @cbawebdesign , Could you open an issue here please: https://github.com/syonip/flutter_fbstorage_video_upload

cbawebdesign commented 3 years ago

sure thanks!!

fguillen-tejera commented 3 years ago

Hello, really nice tutorial! I just had a question regarding the amount of storage that a typical video uses in Firebase Cloud Storage. Thank you!

fguillen-tejera commented 3 years ago

Edit: Also, what would be the pros and cons of going with Publitio in your other tutorial vs. going with Firebase cloud Storage? Thank you so much!

syonip commented 3 years ago

Hi @fguillen-tejera, The file is stored as is, and it's size depends on the length, and level of encoding. e.g. if you have a 10 second video encoded at a bitrate of 2MB per second, it will be 20 MB.

I wouldn't recommend using publitio if you want to upload straight from the client, because you have to put the admin credentials in the client.

syonip commented 3 years ago

@aytunch @fguillen-tejera and anyone else who asked, I just wrote a guide about how to move the encoding to Cloud Functions, you can check it out if you're still interested: https://itnext.io/serverless-video-upload-and-encoding-with-firebase-storage-cloud-functions-and-publitio-a4b2997b1508

The code is here: https://github.com/syonip/flutter_cloud_function_publitio

aytunch commented 3 years ago

@syonip Hi again:) I am using flutter_ffmpeg and the encoding+uploading takes a very long time, especially the encoding part on low end devices. In the "Jank" section you said: "Video encoding is a CPU-intensive job. Because flutter is single-threaded, running ffmpeg encoding will cause jank (choppy UI) while it’s running. The solution is of course to offload the encoding to a background process. Regrettably, I haven’t found a way to do this easily with flutter_ffmpeg" Since you wrote this article, I guess there have been some advancements in Flutter. Do you think we now can encode in a seperate thread or more preferably on a background process? If we could do that, then even if the user puts our app on background, the encoding+uploading would continue. The cool apps do this somehow, so I guess it should be possible. Do you think it is a shortcoming of Flutter? Thanks:D

syonip commented 3 years ago

Hi @aytunch , About the encoding, I think that flutter_ffmpeg does run the process in a background thread on android at least. It does so inside the platform channel of the plugin, so using an isolate won't help. iOS doesn't have any real support for long-running background tasks to this day.

If you want to offload the encoding to a third party API, you can check out this blog post: https://itnext.io/serverless-video-upload-and-encoding-with-firebase-storage-cloud-functions-and-publitio-a4b2997b1508

And if you want to perform the uploading itself in the background, this you can do, as it's supported on the OS level. Read more here: https://medium.com/@syonip/background-video-upload-to-firebase-storage-with-flutter-ee398b796656

Hope this helps :)

louisdeveseleer commented 1 year ago

Thanks a lot for this article, this is super helpful. I was starting to really struggle with setting up firebase-hosted HLS videos and you unblocked me.

syonip commented 1 year ago

Glad you found it useful :)