mrlt8 / docker-wyze-bridge

WebRTC/RTSP/RTMP/LL-HLS bridge for Wyze cams in a docker container
GNU Affero General Public License v3.0
2.56k stars 155 forks source link

Feature Request: Stream HTTP Video as MJPEG #13

Open SomebodySysop opened 3 years ago

SomebodySysop commented 3 years ago

So far, no issues with the app. It currently outputs two http streams: one hls and the other straight http to browser. I have tested both, and both work.

I was wondering if it would be too much trouble to add a 3rd http stream: mjpeg?

I've been trying to do this myself with ffmpeg for days now with no success.

My nvr ContaCam only supports http streams encoded as mjpeg. It won't recognize either http stream currently supported by socker-wyze-bridge. The load on the computer processor (ContaCam only runs on Windows) is far less for http streams than rtsp. Right now, I have to stream some of my cameras to a PC running VLC, then use VLC to trasncode the rtsp streams to http mjpeg streams for ContaCam to read in. If I sent all the streams to this master as rtsp, it would crash. I basically have to do some fancy load balancing to get the streams into my master PC without overloading it. If the docker-wyze-bridge could stream mjpeg, I could eliminate a couple of PCs (one in house, one in garage) and stream everything (9 cameras) directly to the master.

I have tried, without success, to install both Shinobi and Zoneminder for this task. I get them both installed, but all the post-install config requirements to actually get them to run is driving me nuts. I don't even want to use them to monitor. I just want to capture the wyze streams and transcode them to mjpeg.

Anyway, if it could be easily added, great! If not, no problem.

mrlt8 commented 3 years ago

I'll have a look. I actually had another script that would dump keyframes from the camera to a basic flask app before starting this docker.

baudneo commented 3 years ago

If you want help setting up zoneminder go to the r/zoneminder subreddit and ask, there's a user tsp84 there that will help and be patient.

SomebodySysop commented 3 years ago

You think this might be accomplished with the new ffmpeg directive you just added?

And what do we put there? A normal ffmpeg command with everything except "ffmpeg"?

mrlt8 commented 3 years ago

That is one possibility. You could replace rtsp-simple-server with an ffserver docker image and have FFMpeg stream to the ffserver container.

I'm still looking into adding an http server which we might be able to use for both the two-step verification and the mjpeg stream.

SomebodySysop commented 3 years ago

rtsp-simple-server is working perfectly. Last thing I want to do is replace it with deprecated ffserver. Looked into a number of possibilities, including rtsp2mjpg, but none seem to pan out. ffmpeg alone fails because of this: https://www.reddit.com/r/ffmpeg/comments/k1hjm7/tcp_connection_refused_when_attempting_to_stream/geujiz2?utm_source=share&utm_medium=web2x&context=3

Even with listen 1 and/or 2 options.

It appears that having an http server running at the port to which ffmpeg is streaming http will be the best bet. Hope you're able to get that going!

mrlt8 commented 3 years ago

This worked for me, but only seems to work with one camera:

ports:
    - 8080:8080
environment:
    - FFMPEG_CMD=-f h264 -i - -listen 1 -f mjpeg http://0.0.0.0:8080/
    - WYZE_EMAIL=.....
SomebodySysop commented 3 years ago

This worked for me, but only seems to work with one camera:

ports:
    - 8080:8080
environment:
    - FFMPEG_CMD=-f h264 -i - -listen 1 -f mjpeg http://0.0.0.0:8080/
    - WYZE_EMAIL=.....

Awesome! One camera actually working is a better start than I've had so far!

So, I add 8080 (or something) to "ports:"

environment:
    - FFMPEG_CMD=-f h264 -i - -listen 1 -f mjpeg http://localhost:8080/wyzecam05

Then I can pick up the camera at http://localhost:8080/wyzecam05 ?

If this works, seems to me all we'd need to have is ability to add multiple ffmpeg commands. Anyway, I'll try it!

Thank you!

I assume I select the camera using -i option with rtsp stream uri?

mrlt8 commented 3 years ago

You don't need the cam name at the end of your ffmpeg command (it gets added in the script). IIRC, you need to use 0.0.0.0 instead of localhost when inside a docker container

We're already running separate ffmpeg processes for each camera, but it seems like ffmpeg's http server can only have one stream per port (:8080 in the example above).

SomebodySysop commented 3 years ago

Am I doing this right?

       ports:
            - 1935:1935
            - 8554:8554
            - 8888:8888
            - 8080:8080
        volumes:
            - ./app/rtsp-simple-server.yml:/rtsp-simple-server.yml

    wyzecam-bridge:
        container_name: wyze-bridge
        restart: always
        build: 
            context: ./app
            # dockerfile: Dockerfile.arm
        environment:
            - WYZE_EMAIL=...
            - WYZE_PASSWORD=...
            - FILTER_NAMES=WyzeCam302, WyzeCam303, WyzeCam304
            - FFMPEG_CMD=-f h264 -i rtsp://192.168.1.197:8554/wyzecam302 -listen 1 -f mjpeg http://0.0.0.0:8080/           

netstat -tupln tcp 0 0 0.0.0.0:8080 0.0.0.0:* LISTEN 2507/docker-proxy
So, docker is listening to port 8080

There is a rtsp stream at: rtsp://192.168.1.197:8554/wyzecam302 (verified with vlc)

But, nothing at: http://192.168.1.197:8080/ (refused to connect)

mrlt8 commented 3 years ago

You need to open the 8080 port on the wyze-bridge container

mrlt8 commented 3 years ago

You don't need to specify the input as it will be piped in. Just use the FFMpeg command I posted above.

SomebodySysop commented 3 years ago

You don't need to specify the input as it will be piped in. Just use the FFMpeg command I posted above.

OK, got that.

But, how do I open the 8080 port on the wyze-bridge container? The only thing I know to do is edit the docker-compose.yml file. Is there another file somewhere I need to edit?

mrlt8 commented 3 years ago

Just add

ports:
    - 8080:8080

Anywhere under wyzecam-bridge:

SomebodySysop commented 3 years ago

Oh, yes, like exactly in your example. OK, I think I've got it now.

  services:
rtsp-server:
    container_name: rtsp-server
    image: aler9/rtsp-simple-server
    restart: always
    environment: 
        - RTSP_PROTOCOLS=tcp
    ports:
        - 1935:1935
        - 8554:8554
        - 8888:8888
    volumes:
        - ./app/rtsp-simple-server.yml:/rtsp-simple-server.yml

wyzecam-bridge:
    container_name: wyze-bridge
    restart: always
    build: 
        context: ./app
        # dockerfile: Dockerfile.arm
    ports:
      - 8080:8080
    environment:
        - WYZE_EMAIL=...
        - WYZE_PASSWORD=...
        - FILTER_NAMES=WyzeCam302, WyzeCam303, WyzeCam304
        - FFMPEG_CMD=-f h264 -i - -listen 1 -f mjpeg http://0.0.0.0:8080/     
SomebodySysop commented 3 years ago

What do you enter to get to the stream?

http://:8080/ ?

mrlt8 commented 3 years ago

Try http://localhost:8080/wyzecam302?

SomebodySysop commented 3 years ago

I updated my docker-wyze-bridge just in case that was the issue, and I'm seeing a bunch of these "path must end with a slash" errors that I didn't see before:

File docker-compose.yml saved root@ToshibaWin7-Ubuntu:/home/ron/docker/docker-wyze-bridge# docker-compose up Starting rtsp-server ... done Recreating wyze-bridge ... done Attaching to rtsp-server, wyze-bridge rtsp-server | 2021/07/16 04:59:19 I [0/0] rtsp-simple-server v0.16.3 rtsp-server | 2021/07/16 04:59:19 I [0/0] [RTSP] TCP listener opened on :8554 rtsp-server | 2021/07/16 04:59:19 I [0/0] [RTMP] listener opened on :1935 rtsp-server | 2021/07/16 04:59:19 I [0/0] [HLS] listener opened on :8888 rtsp-server | 2021/07/16 04:59:19 I [0/0] [RTSP] [conn 192.168.1.65:50074] opened rtsp-server | 2021/07/16 04:59:19 I [0/0] [RTSP] [conn 192.168.1.65:50074] ERR: no one is publishing to path 'wyzecam303' rtsp-server | 2021/07/16 04:59:19 I [0/0] [RTSP] [conn 192.168.1.65:50074] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50076] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [session 2274327795] opened by 192.168.1.65:50076 rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50076] ERR: path must end with a slash (wyzecam303) rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50076] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [session 2274327795] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50077] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50077] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50075] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50075] ERR: no one is publishing to path 'wyzecam304' rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50075] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50078] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [session 2936553258] opened by 192.168.1.65:50078 rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50078] ERR: path must end with a slash (wyzecam304) rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50078] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [session 2936553258] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50079] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50079] closed wyze-bridge | STARTING DOCKER-WYZE-BRIDGE v0.3.2.1 wyze-bridge | Could not find local cache for user wyze-bridge | Could not find local cache for auth wyze-bridge | Fetching auth from wyze api... rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50073] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50073] ERR: no one is publishing to path 'wyzecam302' rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50073] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50080] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [session 2617421277] opened by 192.168.1.65:50080 rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [session 2617421277] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50080] ERR: path must end with a slash (wyzecam302) rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50080] closed rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50081] opened rtsp-server | 2021/07/16 04:59:20 I [0/0] [RTSP] [conn 192.168.1.65:50081] closed wyze-bridge | Saving auth to local cache... wyze-bridge | Fetching user from wyze api... wyze-bridge | Saving user to local cache... wyze-bridge | Could not find local cache for cameras wyze-bridge | Fetching cameras from wyze api... wyze-bridge | Saving cameras to local cache... wyze-bridge | WHITELIST MODE ON wyze-bridge | STARTING 3 OF 7 CAMERAS

rtsp-server | 2021/07/16 04:59:56 I [2/2] [RTSP] [conn 192.168.1.65:50159] ERR: path must end with a slash (wyzecam303) rtsp-server | 2021/07/16 04:59:56 I [2/2] [RTSP] [conn 192.168.1.65:50159] closed rtsp-server | 2021/07/16 04:59:56 I [2/2] [RTSP] [conn 192.168.1.65:50160] opened rtsp-server | 2021/07/16 04:59:56 I [2/2] [RTSP] [conn 192.168.1.65:50160] closed rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50745] opened rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50745] ERR: no one is publishing to path 'wyzecam303' rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50745] closed rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50746] opened rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [session 183324462] opened by 192.168.1.65:50746 rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50746] ERR: path must end with a slash (wyzecam303) rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50746] closed rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [session 183324462] closed rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50747] opened rtsp-server | 2021/07/16 04:59:59 I [2/2] [RTSP] [conn 192.168.1.65:50747] closed rtsp-server | 2021/07/16 05:00:01 I [2/2] [RTSP] [conn 172.18.0.3:59936] opened rtsp-server | 2021/07/16 05:00:01 I [2/2] [RTSP] [session 330857088] opened by 172.18.0.3:59936 rtsp-server | 2021/07/16 05:00:01 I [3/2] [RTSP] [session 330857088] is publishing to path 'wyzecam303', 1 track with TCP rtsp-server | 2021/07/16 05:00:02 I [3/2] [RTSP] [conn 192.168.1.65:50750] opened rtsp-server | 2021/07/16 05:00:02 I [3/2] [RTSP] [session 452605106] opened by 192.168.1.65:50750 rtsp-server | 2021/07/16 05:00:02 I [3/2] [RTSP] [session 1137853559] opened by 192.168.1.65:50750 rtsp-server | 2021/07/16 05:00:02 I [3/3] [RTSP] [session 1137853559] is reading from path 'wyzecam303', 1 track with TCP

I am assuming this means I need to place a "/" at the end of the rtsp uris used to connect to the bridge?

Problem is, at least with vlc, it won't connect with a back slash at end of uri: rtsp://:8554/camera/ <--- this will not connect

UPDATE:

I found the "end with a slash" answer here: https://github.com/mrlt8/docker-wyze-bridge/issues/5#issuecomment-878692064

mrlt8 commented 3 years ago

Still needs work, but the dev branch has some initial support for mjpeg.

uri should be http://localhost:8080/cam-nickname or to view in the browser http://localhost:8080/mjpeg/cam-nickname

Unfortunately, I had to bring back OpenCV and PyAV which bloats the container and caused some issues on the arm build in the past.

SomebodySysop commented 3 years ago

My initial tries were unsuccessful. And the main rtsp streams became unstable, so I turned off the ffmpeg for now.

mrlt8 commented 3 years ago

Lots of backend changes with the dev branch, so you should probably start with a fresh. See the new docker-compose.sample.yml

gleep52 commented 2 years ago

Any progress on this? I have an older v2 I'd like to use for a specific case but it requires mjpeg streaming... is that something we could get working? All four of my V3's are working great.

mrlt8 commented 2 years ago

mjpeg is pretty niche and resource intensive, so it probably won't be supported.