Jump to content

Auto quality issues in web app


Recommended Posts

Jdiesel
Posted

Thanks for posting this, it seems to have helped with my browser clients using the the auto quality setting when playing remuxes.

Does anyone have any tweaks for adjusting the sensitivity of app endpoint to make the auto selection less conservative? 

  • 5 months later...
Posted
On 7/8/2024 at 7:46 PM, Jdiesel said:

Thanks for posting this, it seems to have helped with my browser clients using the the auto quality setting when playing remuxes.

Does anyone have any tweaks for adjusting the sensitivity of app endpoint to make the auto selection less conservative? 

There's no way to do that unfortunately, apart from building your own patched versions of emby apps.

This is what Emby Android does for example:

define(["exports"], function(_exports) {
    function supportsConnectionTypeDetection() {
        if ("undefined" != typeof navigator) {
            var connection = navigator.connection;
            if (connection) {
                var connectionType = connection.type;
                if (connectionType || void 0 !== connectionType) return !0;
                connectionType = connection.effectiveType;
                if ("slow-2g" === connectionType || "2g" === connectionType || "3g" === connectionType) return !0
            }
        }
        return !1
    }
    Object.defineProperty(_exports, "__esModule", {
        value: !0
    }), _exports.default = void 0;
    _exports.default = {
        supportsConnectionTypeDetection: supportsConnectionTypeDetection,
        getDefaultQuality: function(networkType) {
            switch (networkType) {
                case "wan":
                    return function() {
                        if ("undefined" != typeof navigator) {
                            var connection = navigator.connection;
                            if (connection) {
                                var downlink = connection.downlink;
                                if (downlink && 0 < downlink && downlink < Number.POSITIVE_INFINITY) return downlink = downlink * 1e6 * .7, downlink = parseInt(downlink);
                                if ((downlink = connection.downlinkMax) && 0 < downlink && downlink < Number.POSITIVE_INFINITY) return downlink = downlink * 1e6 * .7, downlink = parseInt(downlink)
                            }
                        }
                        return null
                    }() || (supportsConnectionTypeDetection() ? 12e6 : 4000002);
                case "cellular":
                    return 1000001;
                default:
                    return 2e8
            }
        }
    }
});

 

It uses the same `navigator.connection` attribute, which as defined in the first post - is awful for detecting actual downlink conditions by itself, and it also does the same fallback to 4mbps.

I wish emby provided a better way to hook into this system until a better "auto" is developed. The way I can see the stupid simple intermediary solution is either of these two options:

A. Have all emby apps call the "/bitratetest" endpoint to measure speed. Server admins can optimize this endpoint to provide more realistic speeds. E.g. use cloudflare, caching etc.

B. Provide server admins with an option like "Auto quality multiplier" or "Min auto bitrate" and use it as floor for whatever tests the clients end up with.

Or even both, but I'd take anything at all that gives me, the server admin an ounce of control over this.

  • Like 1
visproduction
Posted

Interesting discussion.  Improvements with all the ideas mentioned would be nice. 

I wonder if the router QOS setting to Highest for WWW applications would help video TCP streaming?  By default, my older Netgear router was set to normal and all IP phone and Google apps were set to highest.  How much difference can this router setting really make?  I assume it only would make a difference during competitive traffic.  It most setups there could be hardly any competitive traffic anyway.  Just a thought.

  • Agree 1
Happy2Play
Posted

Looks like the change has made into other clients now.

 

  • Like 1
Posted (edited)
31 minutes ago, Happy2Play said:

Looks like the change has made into other clients now.

 

If I read this right, this is only for the "fallback" value, which only covers a smaller subset of "auto" users where client doesn't support `navigator.downlink` API (I guess Fire TV and all other weird devices). The larger subset - i.e. clients with downlink API access, will still be tied to whatever nearly always wrong value that API returns, which is then further hit by that * 0.7.

Judging by the code snippet, WAN users with weird devices without downlink API will almost always have better results as it will be that hardcoded 12mbps. And WAN + downlink API users will never get 12mbps, as it's capped to 10mbps - so it stands true even if downlink somehow figures out the proper value (which from my tests, never happened).

Also I only just noticed that cellular users will be hardcoded to 1mbps now? That's... horrifying. Nearly all of my clients have 100+mbps cellular, so now I should expect way more needless transcoding.

To be honest, this change makes things even worse than they were before by making invalid assumptions and I still think Emby should just leave this all up to the server admins / community. We all can probably figure out a better solutions catering to different needs than Emby team trying to come up with some kind of universal value that will work for everyone.

Edited by unmovable
  • Like 2
Happy2Play
Posted
2 minutes ago, unmovable said:

Also I only just noticed that cellular users will be hardcoded to 1mbps now? That's... horrifying. Nearly all of my clients have 100+mbps cellular, so now I should expect way more needless transcoding.

Must be nice as 9 time out of 10 celluar is saturated or throttled around here.  So I can see 1Mbps to 100+ but will expect lots of traffic shaping for provider network as normal.

But in the end the edge case of admins wanting full control of this may or may not happen as to me there will be just as many complains/issue either way the I guess Emby could just push back to USER error and provide no support as it would be an issue of one's own creation.  

But Auto will never be what one thinks it is.

  • Like 1
Posted
Just now, Happy2Play said:

Must be nice as 9 time out of 10 celluar is saturated or throttled around here.  So I can see 1Mbps to 100+ but will expect lots of traffic shaping for provider network as normal.

But in the end the edge case of admins wanting full control of this may or may not happen as to me there will be just as many complains/issue either way the I guess Emby could just push back to USER error and provide no support as it would be an issue of one's own creation.  

But Auto will never be what one thinks it is.

Which highlights why universal assumptions about Emby servers shouldn't be made. They're fine as defaults, but should be configurable as not all world is the same. And Emby is just shifting the "support" to admins with this approach. With 1mbps hardcoded, my users will either:

1. Start complaining to me that "something's wrong with the app" and I have to explain to them to disable "auto" (which some of them may not want to do).

2. Don't understand why their quality is suddenly crap and either live with it or assume that Emby doesn't provide them quality content.

Status quo and new change is shifting the workload onto the server admins who have their hands tied. Most of the admins probably won't ever complain because they won't care or understand why it's happening, and ones that do understand, sit here not quite understanding why we can't control what happens to our servers and have to live by assumptions made in the world where cellular doesn't work well :( 

  • Like 2
Posted
1 hour ago, unmovable said:

Which highlights why universal assumptions about Emby servers shouldn't be made. They're fine as defaults, but should be configurable as not all world is the same. And Emby is just shifting the "support" to admins with this approach. With 1mbps hardcoded, my users will either:

1. Start complaining to me that "something's wrong with the app" and I have to explain to them to disable "auto" (which some of them may not want to do).

2. Don't understand why their quality is suddenly crap and either live with it or assume that Emby doesn't provide them quality content.

Status quo and new change is shifting the workload onto the server admins who have their hands tied. Most of the admins probably won't ever complain because they won't care or understand why it's happening, and ones that do understand, sit here not quite understanding why we can't control what happens to our servers and have to live by assumptions made in the world where cellular doesn't work well :( 

Agree with everything here.

Just yesterday i had a friend contact me and ask if something was wrong since quality was so low or if Emby just couldn't deliver any better. When i tend explain the problem I usually get the "but i thought auto found the best quality so i kept it there thinking it knew best" or just as likely "didn't know i could change quality".
I'm getting pretty tired of having to explain it.

1mpbs or even the new 12mpbs that is the new auto is a joke for the average internet connection here in Denmark, even mobile connections have no problems with much more than that.
Denmark has mostly moved past data caps and (i believe by law) throttling people as well.
I absolutely understand how that might not be the case in the rest of the world but at least give admins a way to set up their server to best match their needs and what their connections can handle.

Lastly, remove the "auto" all together if it's just a fallback/default (don't call it anything at all like fx. "default" either), all it does it create confusion.
I would much rather have to explain how to lower quality than how to raise it.

  • Like 2
  • 5 weeks later...
Posted (edited)
On 3/11/2024 at 10:24 AM, unmovable said:

@cochize1I'm using linuxserver docker container and I've added a custom script (/custom-cont-init.d) that patches the file and sets minimum bitrate to 10mbps when container is started:

#!/usr/bin/with-contenv bash
set -e

manager_path="/app/emby/system/dashboard-ui/modules/common/playback/playbackmanager.js"

# Wait for manager file to exist
while [ ! -f "$manager_path" ]; do
    echo "Waiting for playbackmanager.js to exist..."
    sleep 5
done

# Patch the file
error=$(sed -i 's/function playAfterBitrateDetect(maxBitrate,item,playOptions,onPlaybackStartedFn,signal){/&maxBitrate=Math.max(maxBitrate, 10000001);/' "$manager_path" 2>&1)

# Check if sed command was successful
if [ $? -ne 0 ]; then
    echo "Failed to apply streaming patch. Error: $error"
    exit 1
fi

echo "Streaming patch applied successfully."

 

One odd thing that I noticed is that emby predefined bitrates end with either 1 or 2, which I'm guessing is some sort of special value that is used for some other reasons (maybe resolution?), hence the 10000001 usage in this patch.

 

Something changed in the new beta(4.9.0.37), and the patch doesn't seem to work.

 function playAfterBitrateDetect(maxBitrate,enableAutomaticQuality,item,playOptions,onPlaybackStartedFn,signal)

I noticed that the 'enableAutomaticQuality' variable was added to the code. This seems to be doing something.

error=$(sed -i 's/function playAfterBitrateDetect(maxBitrate,enableAutomaticQuality,item,playOptions,onPlaybackStartedFn,signal){/&maxBitrate=Math.max(maxBitrate, 10000001);/' “$manager_path” 2>&1)

I've tried changing the code to the above, but it doesn't seem to be working.

Edited by hoonlight
  • Like 1
  • 6 months later...
unmovable
Posted

Since new beta, quality detection now lives in a different place.

New patch to hardcode this to 10mbps:

#!/usr/bin/with-contenv bash
set -e

TARGET_FILE="/app/emby/system/dashboard-ui/modules/common/qualitydetection.js"
RETURN_VALUE="10000001"

log_message() {
    echo "[$(date '+%Y-%m-%d %H:%M:%S')] $1"
}

main() {
    log_message "Starting Quality Detection Patcher"

    if [ ! -f "$TARGET_FILE" ]; then
        log_message "✗ ERROR: Target file not found: $TARGET_FILE"
        exit 1
    fi

    if grep -q "getDefaultQuality:function(networkType){return $RETURN_VALUE;" "$TARGET_FILE"; then
        log_message "✓ Already patched - no changes needed"
        exit 0
    fi

    sed -i 's/getDefaultQuality:function(networkType){/getDefaultQuality:function(networkType){return '"$RETURN_VALUE"';/g' "$TARGET_FILE"

    if grep -q "getDefaultQuality:function(networkType){return $RETURN_VALUE;" "$TARGET_FILE"; then
        log_message "✓ PATCH APPLIED SUCCESSFULLY!"
        log_message "✓ Function now returns $RETURN_VALUE immediately"
    else
        log_message "✗ PATCH FAILED!"
        exit 1
    fi
}

main "$@"

 

cochize1
Posted

@unmovablehi, I am not on beta actually but got the same issue as @hoonlight. I am on stable 4.8.11.0 in emby docker now, playbackmanager.js and qualitydetection.js look like the ones I attached in my case. Is your scriplaybackmanager.js pt valid for these? Also, if I wanted to change it manually what should i do?

qualitydetection.js

unmovable
Posted
2 minutes ago, cochize1 said:

@unmovablehi, I am not on beta actually but got the same issue as @hoonlight. I am on stable 4.8.11.0 in emby docker now, playbackmanager.js and qualitydetection.js look like the ones I attached in my case. Is your scriplaybackmanager.js pt valid for these? Also, if I wanted to change it manually what should i do?

qualitydetection.js 1.11 kB · 0 downloads

Yeah, it should work with this too.

You can change the value of RETURN_VALUE - it's bits per second. 

cochize1
Posted

ok, so after injection and emby restart the qualitydetection file looks like this, but when i play i.e iptv from m3u list i still get:
image.png.fb14892a8c81526372235a401128731f.png

define(["exports"], function(_exports) {
    function supportsConnectionTypeDetection() {
        if ("undefined" != typeof navigator) {
            var connection = navigator.connection;
            if (connection) {
                var connectionType = connection.type;
                if (connectionType || void 0 !== connectionType) return !0;
                connectionType = connection.effectiveType;
                if ("slow-2g" === connectionType || "2g" === connectionType || "3g" === connectionType) return !0
            }
        }
        return !1
    }
    Object.defineProperty(_exports, "__esModule", {
        value: !0
    }), _exports.default = void 0;
    _exports.default = {
        supportsConnectionTypeDetection: supportsConnectionTypeDetection,
        getDefaultQuality: function(networkType) {
            return 10000001;
            switch (networkType) {
                case "wan":
                    return function() {
                        if ("undefined" != typeof navigator) {
                            var connection = navigator.connection;
                            if (connection) {
                                var downlink = connection.downlink;
                                if (downlink && 0 < downlink && downlink < Number.POSITIVE_INFINITY) return downlink = downlink * 1e6 * .7, downlink = parseInt(downlink);
                                if ((downlink = connection.downlinkMax) && 0 < downlink && downlink < Number.POSITIVE_INFINITY) return downlink = downlink * 1e6 * .7, downlink = parseInt(downlink)
                            }
                        }
                        return null
                    }() || (supportsConnectionTypeDetection() ? 12e6 : 4000002);
                case "cellular":
                    return 1000001;
                default:
                    return 2e8
            }
        }
    }
});

 

unmovable
Posted

@cochize1 It could be a cached version of that file either in reverse proxy (if you're using one), or browser. If you're not using a reverse proxy, try cleaning your browser cache

cochize1
Posted

@unmovablethat was it, actually both, nginx and browser cache, now it works as intended. I have just one more question, if for some reason any connection from a clients browser will be from lower bandwidth than 10 mpbs the stream will just fail to start (as it is lowest possible now), and would work if client manuallly set up lower quality (or just other than Auto)? 

unmovable
Posted

@cochize1Glad that it worked!

If client has "auto" selected and their actual bandwidth is lower than 10mbps, stream will start, but it will pause for buffering frequently.

If they select manual, lower quality, it should work just fine, this qualitydetection.js won't even be called in that case (at least from what I understand from emby's minified js code).

  • Thanks 1

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...