Merge native codec stack into develop - #509
Conversation
* feat(codec): add native decode node * feat(codec): deprecate h264 decode API * refactor(codec): use simadecode for h264 paths * fix(codec): warn on h264 decode class use * docs(codec): fix simadecode graph snippet * test(graph): fix legacy input policy test
* feat(core): add HTTP MJPEG decoded input * test(groups): cover HTTP MJPEG topology
* feat(rtsp): add encoded input group Add a reusable encoded RTSP source group for H.264 and MJPEG so decoded RTSP inputs and custom app topologies can share the same source/depacketize/parse contract. Refs #495 * fix(rtsp): preserve decoded options source API
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 5e34933303
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
* fix(codec): normalize MJPEG source caps Use the configured MJPEG decode framerate to repair missing or invalid JPEG input caps before native decode. This lets RTSP and HTTP MJPEG decoded inputs accept streams that report framerate=0/1 while preserving strict defaults for other paths. Expose HTTP TLS strictness as an explicit source option so local HTTPS MJPEG streams with non-public certificates can be consumed without hardcoded behavior. Refs #515 * fix(api): preserve HTTP MJPEG option layout
* fix(codec): derive RTSP MJPEG caps fps RTSP MJPEG decoded inputs should not require callers to pass dec_fps when the stream already exposes a usable framerate through SDP. Use the existing encoded caps fixup path to apply the RTSP-derived FPS when no explicit fallback is provided, while keeping explicit dec_fps behavior intact. Refs #527 * fix(codec): match MJPEG SDP payload fps MJPEG auto-caps should derive framerate from the RTP media section selected by the JPEG payload filter, not from the first video media advertised in a mixed SDP.
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: ab9c0405b6
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
* fix(codec): match unfiltered MJPEG SDP fps MJPEG payload filtering can be disabled while the RTP caps still require JPEG encoding. Keep SDP framerate derivation on the JPEG media in that mode instead of falling back to the first video framerate. * fix(codec): preserve static JPEG SDP fps Unfiltered MJPEG RTP caps still select JPEG media. Treat static RTP payload 26 as JPEG when SDP omits rtpmap so auto-caps can use that media framerate instead of falling back to no FPS.
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: fd4b84914d
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
MJPEG auto-caps should use stream-derived SDP framerate before the configured fallback when both are available. Also attach encoded caps fixup probes in pushed-input builds so the public node behaves consistently outside source-owned graphs.
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 8a3b7ae7c0
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
Respect auto_caps_from_stream for MJPEG caps repair by using RTSP SDP FPS only when the source group explicitly enables stream-derived caps. Fallback-only fixups continue to use the configured dec_fps.
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: da9c1a61b9
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
Why
This promotes the native JPEG/MJPEG codec stack from
integration/native-codec-stackintodevelop.Before this work, users had to assemble JPEG/MJPEG source, framing, depacketize, parse, and decode paths themselves. That pushed codec-specific GStreamer details into Apps and made standard RTSP/HTTP camera topologies harder to reuse and test.
After this PR, Core owns reusable public codec graph APIs for native H.264, JPEG, and MJPEG decode in C++ and PyNeat.
User Benefits
SimaDecode.RtspDecodedInputcodec.JpegDecodewhen users explicitly want the softwarejpegdecpath.dec_fpswhen the stream advertises a usable framerate.What Changed
nodes::SimaDecode(...)/pyneat.nodes.sima_decode(...).SimaDecodeOptionsandSimaDecodeType::{H264,JPEG,MJPEG}.nodes::H264Decode(...)/pyneat.nodes.h264_decode(...)for new code while preserving existing H.264 source compatibility.nodes::JpegDecode()/pyneat.nodes.jpeg_decode()as the explicit CPU/GStreamerjpegdecpath.nodes::HttpSource(...)/pyneat.nodes.http_source(...)nodes::MultipartJpegDemux(...)/pyneat.nodes.multipart_jpeg_demux(...)nodes::JpegParse(...)/pyneat.nodes.jpeg_parse(...)nodes::RTPJpegDepacketize(...)/pyneat.nodes.rtp_jpeg_depacketize(...)nodes::groups::HttpMjpegDecodedInput(...)pyneat.groups.http_mjpeg_decoded_input(...)HttpMjpegDecodedInputOptionsHttpMjpegDecodedInputOutputSpec(...)nodes::groups::RtspEncodedInput(...)pyneat.groups.rtsp_encoded_input(...)RtspEncodedInputOptionsRtspEncodedInputOutputSpec(...)RtspCodec::{H264,MJPEG}nodes::groups::RtspDecodedInput(...)pyneat.groups.rtsp_decoded_input(...)RtspDecodedInputOptions::codecRtspDecodedInputOutputSpec(...)ssl_strictoptions for local HTTPS MJPEG sources while keeping strict TLS validation enabled by default.Topologies
HTTP MJPEG decoded input:
RTSP H.264 encoded input:
RTSP MJPEG encoded input:
RTSP decoded input:
H.264 remains the default
RtspDecodedInputcodec.Included PRs
H264Decodecompatibility deprecation.Issue Coverage
Validation
Validation was performed in the staged PRs before promotion into
develop.Covered validation includes:
SimaDecode.Current PR CI was still running when this body was drafted.
Risk
This PR adds public codec APIs and extends RTSP decoded input behavior.
H.264 remains the default RTSP decoded codec, so existing H.264 users should remain source-compatible. H.265 is intentionally not part of this stack.
Follow-up
Live codec runtime coverage remains tracked under #507 for broader RTSP H.264, RTSP MJPEG, HTTP MJPEG, performance, determinism, and accuracy validation.
Refs #197
Refs #437
Refs #436
Refs #448
Refs #495
Refs #449
Refs #438
Refs #515
Refs #527