Skip to content

add zstd and snappy compression for query api #6848

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 11 commits into
base: master
Choose a base branch
from

Conversation

afhassan
Copy link
Contributor

@afhassan afhassan commented Jun 27, 2025

What this PR does:

  • Add Snappy and Zstd compression for querier -> QFE responses.
  • Use a new internal http header X-Uncompressed-Length to enforce QFE response size limit before decompressing response

Which issue(s) this PR fixes:
Fixes #

Checklist

  • Tests updated
  • Documentation added
  • CHANGELOG.md updated - the order of entries should be [CHANGE], [FEATURE], [ENHANCEMENT], [BUGFIX]

@afhassan afhassan marked this pull request as ready for review July 9, 2025 23:20
Copy link
Contributor

@erlan-z erlan-z left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added small nit, but overall looks good to me.
Thanks.

@afhassan
Copy link
Contributor Author

@yeya24 @SungJin1212 could someone take a look when you have some time? Thanks!

@SungJin1212
Copy link
Member

SungJin1212 commented Jul 25, 2025

@afhassan
Thanks for the contribution. The code looks nice. Can you add an e2e test?
I think it would be good to add tests to TestQuerierResponseCompression.

@afhassan
Copy link
Contributor Author

afhassan commented Jul 26, 2025

@SungJin1212 Thanks for the review, I added unit tests and an integration test for compression. The change done to QFE response size limit is already covered by this test https://github.com/afhassan/cortex/blob/master/integration/query_frontend_test.go#L977

@@ -102,8 +110,23 @@ func (c instantQueryCodec) DecodeResponse(ctx context.Context, r *http.Response,
return nil, err
}

responseSize := 0
responseSizeHeader := r.Header.Get("X-Uncompressed-Length")
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This change means that we need a two phase deployment for querier to return this header for Query Frontend to properly apply the response size limit. Otherwise, the value is 0.

I think we should find a way (maybe a flag) to properly maintain the previous behavior during rollout.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I didn't quite get it, do you mean during deployment if Query Frontend is updated first then the limit wouldn't apply because the header is not being returned from Querier?

The old behaviour only works for gzip which is why I changed it. I can reverse it to use the old behaviour when gzip is used and the new one for other compression types.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. If we use gzip then this limiter won't work until Querier is updated, which is a breaking behavior.

We just need a way to fallback to the old behavior if it is gzip. Other types are fine since they are new

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If header is missing we now fallback to applying limit using size of the response after decoding it. I think this is a cleaner way to still apply the limit and avoid a breaking change if the header is not there.

Applying the limit before decoding response was an optimization in the old behaviour, but I don't think it is considered breaking if we are still applying the limit.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants