PHPackages                             52-entertainment/302 - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [HTTP &amp; Networking](/categories/http)
4. /
5. 52-entertainment/302

ActiveProject[HTTP &amp; Networking](/categories/http)

52-entertainment/302
====================

A redirect balancer between several hosts.

1.0(4y ago)102[1 PRs](https://github.com/52-entertainment/302-balancer/pulls)MITPHPPHP &gt;=8.0CI passing

Since Apr 19Pushed 8mo ago3 watchersCompare

[ Source](https://github.com/52-entertainment/302-balancer)[ Packagist](https://packagist.org/packages/52-entertainment/302)[ RSS](/packages/52-entertainment-302/feed)WikiDiscussions main Synced today

READMEChangelog (1)Dependencies (13)Versions (3)Used By (0)

[![CI Workflow](https://github.com/52-entertainment/302-balancer/actions/workflows/ci-workflow.yml/badge.svg)](https://github.com/52-entertainment/302-balancer/actions/workflows/ci-workflow.yml)[![Codecov](https://camo.githubusercontent.com/eadd7529a4da656653f22452f572366988cbe5c4b3eba8b9e9b40402c96884c6/68747470733a2f2f636f6465636f762e696f2f67682f35322d656e7465727461696e6d656e742f3330322d62616c616e6365722f6272616e63682f6d61696e2f67726170682f62616467652e7376673f746f6b656e3d504a616e4173646e6e41)](https://codecov.io/gh/52-entertainment/302-balancer)

302
===

[](#302)

This is a load balancer that doesn't *act* as a load balancer.

It is a *redirect* balancer. Instead of forwarding traffic to a specific host/port, it returns a 302 response with a different location.

Typical usage is that your entrypoint is `https://example.com/foo` and you want to redirect your traffic to a pool made of `https://01.example.com` and `https://02.example.com`, by keeping path and query string intact.

It is built with **PHP 8** on top of [ReactPHP](https://reactphp.org/). Because it answers very short responses and runs within a loop, it can easily handle thousands of requests/s without blinking an eye.

Build
-----

[](#build)

Build is optional (you can simply run `php bin/console serve`) but will produce an optimized, single-file executable PHAR.

PHP 8, Composer and [Box](https://github.com/box-project/box/blob/master/doc/installation.md) are globally required on your computer.

To build the application, run:

```
./bin/build
```

It will land in `bin/302`.

Usage
-----

[](#usage)

### Live balancing (no persistence - for testing purposes or prototyping)

[](#live-balancing-no-persistence---for-testing-purposes-or-prototyping)

```
php bin/302 serve \
--host=0.0.0.0 \
--port=8080 \
--pick=random \ # or round-robin
example1.org \
example2.org \
example3.org
```

```
GET http://0.0.0.0:8080/foo?bar=baz

HTTP/1.1 302 Found
Location: http://example2.org/foo?bar=baz
```

### Persisted storage (Redis)

[](#persisted-storage-redis)

```
# Expose the REDIS_DSN variable if necessary, default is:
export REDIS_DSN="redis://localhost:6379"
php bin/302 serve --host=0.0.0.0 --port=8080
```

*App will run, but user agent will get 503 errors because the server pool is empty.*

#### Add a server to the pool

[](#add-a-server-to-the-pool)

```
php bin/302 server:add example1.org
```

*This command can be run while `302 serve` is running, no need to restart the app!*

#### Remove a server from the pool

[](#remove-a-server-from-the-pool)

```
php bin/302 server:remove example1.org
```

*This command can be run while `302 serve` command is running, no need to restart the app!*

#### List servers in the pool

[](#list-servers-in-the-pool)

```
php bin/302 server:list
```

Tests
-----

[](#tests)

```
./vendor/bin/pest
```

Deployment
----------

[](#deployment)

### Example Supervisor config

[](#example-supervisor-config)

After [building the app](#build), you can easily create a supervisor recipe to load it on startup:

```
[program:302]
command=php /usr/local/bin/302 serve --host=127.0.0.1 --port=80%(process_num)02d
user=www-data
numprocs=4
startsecs=1
autostart=true
autorestart=true
process_name=%(program_name)s_%(process_num)02d
environment = APP_LOG_DIR=/var/log/302
```

With the above config, **302** will run on `127.0.0.1:8000`, `127.0.0.1:8001`, `127.0.0.1:8002` and `127.0.0.1:8003`.

Round-robin will be shared across the instances (since they share the same Redis instance).

### CORS / SSL termination

[](#cors--ssl-termination)

**302** has no built-in CORS nor SSL termination, but this can be handled by any web server with reverse-proxy capabilities (Apache, Nginx, Caddy, ...).

#### Caddyfile example

[](#caddyfile-example)

If you're using [Caddy](https://caddyserver.com/), here's an example `Caddyfile`:

```
example.org {
    @get {
        method GET
    }
    @options {
        method OPTIONS
    }
    header Access-Control-Allow-Origin *
    header Access-Control-Allow-Redirect true
    respond @options 200
    reverse_proxy @get 127.0.0.1:8000 127.0.0.1:8001 127.0.0.1:8002 127.0.0.1:8003
}

```

###  Health Score

32

—

LowBetter than 74% of packages

Maintenance43

Moderate activity, may be stable

Popularity8

Limited adoption so far

Community8

Small or concentrated contributor base

Maturity58

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Unknown

Total

1

Last Release

1797d ago

### Community

Maintainers

![](https://www.gravatar.com/avatar/acdd1a8ee0e657ddd06cf11f98a32100ef7121afb8aa270a5b295f5c29c038b3?d=identicon)[bpolaszek](/maintainers/bpolaszek)

---

Top Contributors

[![bpolaszek](https://avatars.githubusercontent.com/u/5569077?v=4)](https://github.com/bpolaszek "bpolaszek (29 commits)")

---

Tags

52

###  Code Quality

TestsPest

Static AnalysisPHPStan

Code StylePHP\_CodeSniffer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/52-entertainment-302/health.svg)

```
[![Health](https://phpackages.com/badges/52-entertainment-302/health.svg)](https://phpackages.com/packages/52-entertainment-302)
```

###  Alternatives

[mshauneu/php-rdkafka-bundle

Integrates php-rdkafka with Symfony2|3

1426.8k](/packages/mshauneu-php-rdkafka-bundle)[p2/ratchet-bundle

Symfony WebSocket bundle using the Ratchet WebSocket library

265.8k](/packages/p2-ratchet-bundle)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
