{"id":36494322,"url":"https://github.com/thylong/whitelist","last_synced_at":"2026-01-12T01:59:30.872Z","repository":{"id":81248741,"uuid":"196598173","full_name":"thylong/whitelist","owner":"thylong","description":"Whitelist is a very simple IP whitelisting microservice acting as a reverse proxy. Its purpose is educational.","archived":false,"fork":false,"pushed_at":"2019-07-14T14:19:35.000Z","size":2981,"stargazers_count":2,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2024-06-20T03:50:59.083Z","etag":null,"topics":["benchmark","educational","educational-project","go","http-service","ip","whitelisting"],"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/thylong.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":"2019-07-12T14:59:13.000Z","updated_at":"2020-07-24T19:44:20.000Z","dependencies_parsed_at":null,"dependency_job_id":"e196f572-39ee-48d0-ac73-410ff94140fc","html_url":"https://github.com/thylong/whitelist","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/thylong/whitelist","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thylong%2Fwhitelist","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thylong%2Fwhitelist/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thylong%2Fwhitelist/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thylong%2Fwhitelist/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/thylong","download_url":"https://codeload.github.com/thylong/whitelist/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thylong%2Fwhitelist/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28331489,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-12T00:36:25.062Z","status":"ssl_error","status_checked_at":"2026-01-12T00:36:15.229Z","response_time":60,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"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":["benchmark","educational","educational-project","go","http-service","ip","whitelisting"],"created_at":"2026-01-12T01:59:30.754Z","updated_at":"2026-01-12T01:59:30.867Z","avatar_url":"https://github.com/thylong.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Whitelist [![GoDoc](https://godoc.org/github.com/thylong/whitelist?status.svg)](https://godoc.org/github.com/thylong/whitelist) [![Go Report Card](https://goreportcard.com/badge/github.com/thylong/whitelist)](https://goreportcard.com/report/github.com/thylong/whitelist)\n\nWhitelist is a very simple IP whitelisting microservice acting as a reverse proxy.  Its purpose is educational, it helps to highlight the importance of using the right algorithm/datastructure in the right context.\n\nIts storage can be either a [hashmap](https://en.wikipedia.org/wiki/Hash_table), a [list](https://en.wikipedia.org/wiki/Array_data_structure) or a [Radix trie](https://en.wikipedia.org/wiki/Radix_tree) depending on what performance you want have.\n\n## How does the service work?\n\nThe service keeps in-memory a whitelist of IPs to let go through the reverse proxy.\nIt's possible to edit through HTTP calls that list without reloads.\n\n2 HTTP servers are exposed for these interactions :\n\n- The first one, on port `8080` is the reverse proxy that filters all incoming requests prior to fan out in the backend service.\n- The second one, on port `8081` is a small API usable to insert/delete/lookup on the whitelist storage.\n\nStorage can be either\n\n### Features \n\n- Storage can be either a hashmap, a list or a Radix trie\n- IP format validation\n- Ipv4 and IPv6 are both supported\n- 100% tests coverage\n- Benchmarks\n- Support TrueIP \u0026 X-Forwarded-For headers\n- Hot whitelisting edition\n- Speed/scalability oriented (use Radix tries by default)\n\n### Schema\n\n```sh\nHTTP request    +-------------+       +-----------+\n                |             |       |           |\n         +-----\u003e+  Whitelist  +------\u003e+  Backend  |\n                |   service   |       |  service  |\n                |             |       |           |\n                +-------------+       +-----------+\n```\n\n### Interacting with the whitelist\n\n\n```sh\n# Insert an IP in the whitelist :\ncurl -X POST http://localhost:8081/ip/\u003cip_address\u003e\n\n# Lookup for an IP in the whitelist :\ncurl -X GET http://localhost:8081/ip/\u003cip_address\u003e\n\n# Delete an IP in the whitelist :\ncurl -X DELETE http://localhost:8081/ip/\u003cip_address\u003e\n```\n\n### Using the proxy\n\nAll calls made to the port `8080` will be forwarded to the backend (dummy by default) after running through the internal\nlogic described in this schema :\n\n```sh\n      +---------------+          +----------------+   yes\n      |               |          |                |          +-------------+\n+-----\u003e  Detect the   +----------\u003e  Is the IP     +----------\u003e Forward to  |\n      |  origin IP    |          |  whitelisted?  |          | the backend |\n      |               |          |                |          +-------------+\n      +---------------+          +-------+--------+\n                                         |\n                                         | no\n                                         |\n                                         |\n                                  +------v--------+\n                                  | Access Denied |\n                                  +---------------+\n```\n\n## Benchmark results\n\nThe results of these tests highly depends on the platform it runs on. The following results are found on my machine:\n```sh\n# HTTP server\nBenchmarkFilterWithRadixSingleIPWhitelist-4   \t   10000\t    152451 ns/op\nBenchmarkFilterWithRadixLargeIPWhitelist-4    \t   10000\t    225666 ns/op\nBenchmarkFilterWithListSingleIPWhitelist-4    \t   20000\t     98824 ns/op\nBenchmarkFilterWithListLargeIPWhitelist-4     \t    5000\t    245444 ns/op\n# Raw whitelisting functions\nBenchmarkListInsert-4     \t10000000\t       172 ns/op\nBenchmarkHMInsert-4       \t100000000\t        14.8 ns/op\nBenchmarkRadixInsert-4    \t50000000\t        27.4 ns/op\nBenchmarkListContain-4    \t    2000\t   1031950 ns/op\nBenchmarkHMContain-4      \t100000000\t        14.8 ns/op\nBenchmarkRadixContain-4   \t20000000\t        88.3 ns/op\n```\n\n## Usage\n\nTo get a sense of the difference of the time complexity of each algorithm, you can simply run the benchmark tests.\nThese tests compare the basic operations possible on the service with small and large sets of whitelisted IPs.\n\nIf you want to experience the service under real conditions, replace the **dummy** service content in the docker-compose\nby the service of your choice.\n\nThen start all services :\n\n```sh\ndocker-compose up\n```\n\nThen seed the whitelist :\n\n```sh\ndocker-compose exec -it tester ash\n# Once attached to the tester container (required to be in Docker network space)\ncurl -X POST http://localhost:8081/ip/\u003cip_address\u003e\n```\n\nAnd then query the backend service :\n\n```sh\n# Still attached to the tester container\ncurl --header \"X-Forwarded-For: \u003cip_address\u003e\" http://localhost:8080/\n```\n\n## Running tests\n\n```sh\n# Run all tests\nmake test\n\n# Run only functionnal tests\nmake test-func\n\n# Run only benchmark tests\nmake test-bench\n\n# Run only end-to-end tests (requires Docker + docker-compose)\nmake test-e2e\n```\n\n## Contribute\n\nContributions are welcome and actually encouraged !\nDon't hesitate to open issues, pull requests, we'll take a look as soon as possible to improve the project.\n\n### How to contribute?\n\nEvery little effort counts.\nFeel free to suggest documentation improvements, fix typos or add new features, even copy a subset of the project !\n\nJust make sure :\n- You're aware of the Licence boundaries (as small as they actually are).\n- For new features: you test the code you'd like to introduce\n- If you'd like to introduce new dependencies, open first an issue\n\n### It's your first open source contribution?\n\nAwesome, welcome !\nHave a look to this guide [here](https://github.com/github/opensource.guide/blob/master/CONTRIBUTING.md) first.\n\n## License\n\n[MIT License](https://github.com/BackMarket/whitelist/blob/master/LICENSE)\n\n## Credits\n\n`ip.go` \u0026 `ip_test.go` were written by [tomasen](https://github.com/tomasen) in its package [realip](https://github.com/tomasen/realip)","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fthylong%2Fwhitelist","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fthylong%2Fwhitelist","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fthylong%2Fwhitelist/lists"}