{"id":20979017,"url":"https://github.com/1pkg/hedgehog","last_synced_at":"2025-12-29T11:50:49.025Z","repository":{"id":144325988,"uuid":"364694840","full_name":"1pkg/hedgehog","owner":"1pkg","description":"Hedgehog 🦔: http hedged transport in go","archived":false,"fork":false,"pushed_at":"2021-05-17T17:18:42.000Z","size":1443,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-01-20T06:20:14.296Z","etag":null,"topics":["go","golang","hedged","hedging","http","requests"],"latest_commit_sha":null,"homepage":"","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/1pkg.png","metadata":{"files":{"readme":"README.MD","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2021-05-05T20:13:48.000Z","updated_at":"2021-05-05T20:28:11.000Z","dependencies_parsed_at":null,"dependency_job_id":"c4c68203-d92c-4924-946e-39d5619b548d","html_url":"https://github.com/1pkg/hedgehog","commit_stats":null,"previous_names":[],"tags_count":1,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/1pkg%2Fhedgehog","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/1pkg%2Fhedgehog/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/1pkg%2Fhedgehog/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/1pkg%2Fhedgehog/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/1pkg","download_url":"https://codeload.github.com/1pkg/hedgehog/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":243382785,"owners_count":20282008,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["go","golang","hedged","hedging","http","requests"],"created_at":"2024-11-19T05:10:33.644Z","updated_at":"2025-12-29T11:50:48.988Z","avatar_url":"https://github.com/1pkg.png","language":"Go","readme":"\u003cp align=\"center\"\u003e\n    \u003cimg src=\"https://raw.githubusercontent.com/1pkg/hedgehog/master/gopher.png?nocache\" alt=\"gohalt\"/\u003e\n\u003c/p\u003e\n\n# Hedgehog 🦔: http hedged transport in go\n\n[![lint](https://github.com/1pkg/hedgehog/workflows/lint/badge.svg)](https://github.com/1pkg/hedgehog/actions?query=workflow%3Alint+branch%3Amaster+)\n[![build](https://github.com/1pkg/hedgehog/workflows/build/badge.svg)](https://github.com/1pkg/hedgehog/actions?query=workflow%3Abuild+branch%3Amaster+)\n[![report](https://goreportcard.com/badge/github.com/1pkg/hedgehog?nocache)](https://goreportcard.com/report/github.com/1pkg/hedgehog)\n[![version](https://img.shields.io/github/go-mod/go-version/1pkg/hedgehog?nocache)](https://github.com/1pkg/hedgehog/blob/master/go.mod)\n[![license](https://img.shields.io/github/license/1pkg/hedgehog?nocache)](LICENSE)\n\n`go get -u github.com/1pkg/hedgehog`\n\n## Details\n\nHedgehog provides hedged http transport decorator to reduce [tail latency at scale](https://cacm.acm.org/magazines/2013/2/160173-the-tail-at-scale/fulltext). Hedged transport makes hedged http calls for matching http resource up to calls+1 times, where initial http call starts right away and then all hedged calls start together after delay calculated by resource. Hedged transport processes and returns first successful http response all other requests in flight are canceled, in case all hedged response failed it simply returns first occurred error. If no matching resources were found - hedged transport simply calls underlying transport.\n\n```go\nhedgehog.NewHTTPClient(\n    http.DefaultClient,\n    // will initiate 2+1 hedged http request.\n    2,\n    // for GET /profile/[0-9] initiate hedged request only after flat 1ms.\n    NewResourceStatic(http.MethodGet, regexp.MustCompile(`profile/[0-9]`), ms_1, http.StatusOK),\n    // for POST /profile initiate hedged request starting with flat 5ms, but after 40/4 calls use aggregated average latency.\n    NewResourceAverage(http.MethodPost, regexp.MustCompile(`profile`), ms_5, 40, http.StatusOK),\n    // for Delete /profile initiate hedged request starting with flat 5ms, but after 50/2 calls use aggregated p30 latency.\n    NewResourcePercentiles(http.MethodDelete, regexp.MustCompile(`profile`), ms_5, 0.3, 50, http.StatusOK),\n).Get(\"http://example.com/profile/5\")\n```\n\nThere are multiple different http hedged resource types to control hedging behavior.\n\n| Resource | Definition | Description |\n|---|---|---|\n| static | `func NewResourceStatic(method string, url *regexp.Regexp, delay time.Duration, allowedCodes ...int) Resource` | Returned resource always waits for static specified delay.\u003cbr\u003e The resource matches each request against both provided http method and full url regexp.\u003cbr\u003e The resource checks if response result http code is included in provided allowed codes, if it is not it returnes `ErrResourceUnexpectedResponseCode`. |\n| average | `func NewResourceAverage(method string, url *regexp.Regexp, delay time.Duration, capacity int, allowedCodes ...int) Resource` | Returned resource dynamically adjusts wait delay based on received successful responses average delays.\u003cbr\u003e The resource is starting to use dynamically adjusted wait delay only after capacity/4 calls.\u003cbr\u003e The resource matches each request against both provided http method and full url regexp.\u003cbr\u003e The resource checks if response result http code is included in provided allowed codes, if it is not it returnes `ErrResourceUnexpectedResponseCode`. |\n| percentiles | `func NewResourcePercentiles(method string, url *regexp.Regexp, delay time.Duration, percentile float64, capacity int, allowedCodes ...int) Resource` | Returned resource dynamically adjusts wait delay based on received successful responses delays percentiles.\u003cbr\u003e The resource is starting to use dynamically adjusted wait delay only after capacity/2 calls, if more than provided capacity calls were received, first half of delay percentiles buffer will be flushed.\u003cbr\u003e Returned resource matches each request against both provided http method and full url regexp.\u003cbr\u003e Returned resource checks if response result http code is included in provided allowed codes, if it is not it returnes `ErrResourceUnexpectedResponseCode`. |\n\n## Licence\n\nHedgehog is licensed under the MIT License.  \nSee [LICENSE](LICENSE) for the full license text.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2F1pkg%2Fhedgehog","html_url":"https://awesome.ecosyste.ms/projects/github.com%2F1pkg%2Fhedgehog","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2F1pkg%2Fhedgehog/lists"}