Self-hosted service
alibaba/tengine avatar
alibaba/tengine

Tengine: an nginx-compatible web server with HTTP/3, Kubernetes Ingress and SM2/TLCP

A high-performance web server and reverse proxy, 100% compatible with nginx.

13,384 stars2,505 forksCBSD-2-Clause

At a glance

What is it?
Tengine is Alibaba's fork of nginx, adding QUIC, dynamic upstream configuration through tengine-ingress, active health checks and Chinese cryptographic algorithms. Here is what the repository actually documents, and where it stops.
Who is it for?
Adopt Tengine if you already run nginx configuration and need HTTP/3, active upstream health checks, dynamic upstream changes through tengine-ingress, or SM2/SM3/SM4 TLCP support for Chinese regulatory environments. Do not adopt it if you want a small, single-purpose proxy: the feature list is long, several of the headline items only exist when the tengine-ingress controller is in the picture, and the container image advertises a dynamic perl module it does not ship.
Can I use it commercially?
Yes. BSD-2-Clause is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 22 days ago.
What is it written in?
Mainly C, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on September 29, 2026, and from our analysis. They are not legal advice.

DEEP OPEN-SOURCE ANALYSIS

What Tengine adds on top of nginx, and who that is for

The README is explicit about the baseline: Tengine inherits all features of nginx-1.31.5 and is described as 100% compatible with nginx. That compatibility claim is the whole pitch. If you have an nginx.conf, a set of upstream blocks and a deployment pipeline built around them, the migration story is that you keep them.

The additions fall into a few groups. Protocol level: HTTP/3 over QUIC v1 and draft-29 using xquic, and NTLS/TLCP dual-certificate TLS with the Chinese SM2, SM3 and SM4 algorithms via Tongsuo. Operations level: active health checks of upstream servers, more load balancing methods (consistent hashing, session persistence, and a weighted round-robin the README describes as O(1) time and O(n) memory), enhanced monitoring with asynchronous log and rollback, DNS caching and memory usage reporting, and fine-grained timing variables for each stage of the upstream interaction.

Then there is a large group that only works with tengine-ingress, the Kubernetes Ingress controller for Tengine. Dynamic configuration of servers, locations and upstreams without reloading or restarting worker processes, per-server-name TLS protocol selection, timeout and CORS settings, routing on header, cookie or query parameter values, weighted multi-upstream routing, failover to a backup upstream by response status code. Roughly a dozen bullets in the feature list are gated on that separate project.

The intended audience is therefore narrower than "anyone running a web server". It is teams running nginx at a scale where reloading worker processes is a real cost, teams that need HTTP/3 without waiting for their distribution's nginx build, and teams that need TLCP because a Chinese regulator or a Chinese partner requires it. For a single static site, none of this is relevant.

How the compatibility and the extensions fit together mechanically

Tengine is a fork of the nginx source tree, not a wrapper around it. The repository layout shows the familiar nginx build system: a configure script at the top level, auto/ for the build machinery, src/ for the server, modules/ for the extensions, conf/ for the default configuration, and html/ for the default pages. Anyone who has built nginx from source will recognise the shape immediately.

The extensions are compiled in as modules. Lua support is the dynamic scripting language the README describes as efficient and suited to extending core functionality. The input body filter mechanism is aimed at writing Web Application Firewalls, because it lets a module inspect and modify the request body before it reaches the upstream. The limit_req module is extended with whitelist support and allows more conditions in a single location. The CONNECT HTTP method is supported for forward proxy use, which is a capability stock nginx does not expose in the same way.

The container build is where the dependency story becomes concrete. The Dockerfile is multi-stage: the builder compiles pinned third-party dependencies (Tongsuo for NTLS, xquic for QUIC and HTTP/3, LuaJIT plus the resty Lua libraries) and Tengine itself, while the runtime stage keeps only the installed tree and the shared libraries it needs. The comment in the Dockerfile states that the configure arguments come from packages/build/configure-args.sh, the same file the rpm, deb and apk recipes use, so the image and the distribution packages ship an identical feature set and filesystem layout. That is a deliberate choice and it is the reason a Tengine container and a Tengine .deb behave the same way.

One detail in that Dockerfile is worth reading carefully. ngx_http_perl_module is always built as a dynamic module, and its two files are set aside in /out-perl by the builder; the default runtime simply does not copy them. The stated consequence is that tengine -V in the default image lists --with-http_perl_module=dynamic even though the .so is not present. The Dockerfile notes this mirrors what nginx's own images do. It is a small trap for anyone who parses tengine -V output to decide what is available.

Installing Tengine with Docker and serving a first server block

The README gives container images as the first installation route. Multi-arch images for amd64 and arm64 with Tongsuo, xquic and Lua are published on every release, in a Debian flavour and a smaller Alpine flavour. Pull and run:

bash
docker pull ghcr.io/alibaba/tengine:latest
docker run --rm -p 8080:80 ghcr.io/alibaba/tengine:latest

After the run command, the server is listening on host port 8080 mapped to container port 80. The README states the server runs as /usr/sbin/tengine with /etc/tengine/tengine.conf, and that you drop your own server blocks into /etc/tengine/conf.d/. So the practical workflow is to mount a directory over /etc/tengine/conf.d/ rather than editing the main configuration file. A minimal server block file placed there would look like this:

code
server {
    listen 80;
    server_name example.com;
    location / {
        root /usr/share/tengine/html;
        index index.html;
    }
}

If you prefer not to use containers, every release ships .rpm, .deb and .apk packages for RHEL, Rocky, Alma, Anolis, openEuler, SLES, Debian, Ubuntu and Alpine on x86_64 and aarch64, attached to the release page. The README's example for RHEL-family systems is:

bash
dnf install https://github.com/alibaba/tengine/releases/download/3.2.0/tengine-3.2.0-<ts>.el9.x86_64.rpm

The <ts> placeholder is part of the filename as published, not something to invent. The README notes these packages install alongside a distribution nginx without conflicting, and points to packages/build/README.md for the exact feature set and for building the packages yourself. Building from source starts from the tarball at tengine.taobao.org or a checkout of the GitHub repository, then the usual nginx-style configure and make.

Where Tengine is the wrong tool

The first limitation is structural: a large share of the advertised dynamic behaviour is not in this repository. Dynamic server, location and upstream configuration, per-server-name TLS protocol selection, header and cookie based routing, weighted upstream routing, failover by status code, and the timeout, CORS and robots toggles are all attributed to tengine-ingress in the README. If you are not running Kubernetes, or you are not willing to adopt that controller, those bullets do not apply to you. What remains is a fork of nginx with HTTP/3, TLCP, health checks, extra balancing methods and a pile of operational conveniences.

The second is the release state. The most recent releases listed are 3.2.0-rc5 from 2026-09-04, 3.2.0-rc4 from 2026-09-01 and 3.2.0-rc3 from 2026-08-11. These are release candidates. The README's installation section refers to 3.2.0 in the package URL, but the release list shows only rc builds at that version. Anyone who needs a stable tag should check the release page rather than assume 3.2.0 final exists.

The third is the fork itself. Tengine tracks nginx-1.31.5 as its base. Every upstream nginx security fix has to be merged, and the time between an nginx advisory and a Tengine release is not documented in the README or the release notes. Teams with a hard patch SLA should treat that as an open question and check the CHANGES and CHANGES.te files in the repository, which are the project's own record of what landed when.

Finally, the feature list is long enough that the build matters more than the project name. A Tengine built without Tongsuo has no TLCP. A Tengine built without xquic has no HTTP/3. The README's own container documentation shows that the default image carries a dynamic perl module entry in tengine -V that does not correspond to a shipped .so. Reading the version banner is not a reliable inventory.

Tengine vs nginx and vs OpenResty: the actual difference in approach

Against nginx, the difference is that Tengine is a superset maintained by a different team. The base is nginx-1.31.5, and the additions are the ones listed above. There is no architectural divergence to weigh: same configuration language, same module model, same process structure. The trade-off is that you depend on the Tengine team to track nginx releases, and you get features nginx does not ship, such as the CONNECT forward proxy method, active health checks built in rather than in a commercial build, and TLCP.

Against OpenResty, the difference is where the extensibility lives. OpenResty is built around Lua and its own module ecosystem; Tengine also supports Lua, and the README calls it a dynamic scripting language that makes it easy to extend core functionalities, but Lua is one item in a much longer list rather than the organising principle. Tengine's other extension points are C-level: the input body filter for WAF-style request inspection, and the module system inherited from nginx. If your plan is to write most of your logic in Lua, the two projects overlap heavily and the choice comes down to which one's surrounding tooling you prefer. If your plan is to write a C module that manipulates request bodies, Tengine's input body filter is the more direct fit.

A third comparison worth making is against the distribution's own nginx packages. Tengine ships .rpm, .deb and .apk packages that the README says install alongside a distribution nginx without conflicting. That means you can evaluate it on the same host without tearing down your existing server, which is a lower-risk path than replacing a working nginx install outright.

Maintenance, licensing and what an upgrade actually costs

The repository is not archived, and the last push was on 2026-09-07. Release candidates have been landing through August and September 2026, so the project is being worked on. The README describes it as actively developed by a team whose core members come from Taobao, Sogou and other Internet companies, and notes the project has been open source since December 2011.

Upgrade cost is dominated by the dependency chain rather than by Tengine itself. The Dockerfile compiles pinned third-party dependencies: Tongsuo for NTLS, xquic for QUIC and HTTP/3, LuaJIT and the resty Lua libraries. A Tengine upgrade that moves any of those pins means rebuilding the image, and the Dockerfile comment notes the build is long enough that the perl variant was designed to avoid a second 90-minute build. If you build from source rather than consuming the published packages, budget for that.

The licence is BSD-2-Clause, which is permissive and broadly compatible with commercial deployment. The bundled third-party components have their own licences, and the Dockerfile explicitly names Tongsuo, xquic and LuaJIT as separate projects. If you redistribute a Tengine image or package, those licences travel with it. That is a statement about what the repository shows, not legal advice; check the actual licence files for each dependency before you ship.

The repository carries CHANGES, CHANGES.cn and CHANGES.te as separate files. The .te file is the project's own changelog for its additions on top of nginx, which is the file to read when you want to know what changed between two Tengine releases rather than between two nginx releases.

Editorial conclusion

Adopt Tengine if you already run nginx configuration and need HTTP/3, active upstream health checks, dynamic upstream changes through tengine-ingress, or SM2/SM3/SM4 TLCP support for Chinese regulatory environments. Do not adopt it if you want a small, single-purpose proxy: the feature list is long, several of the headline items only exist when the tengine-ingress controller is in the picture, and the container image advertises a dynamic perl module it does not ship. Before rolling it out, run tengine -V on your chosen build, confirm which of Tongsuo, xquic and the Lua modules are actually compiled in, and check whether your distribution's nginx packages would conflict with the .rpm or .deb Tengine ships. Verify the CONNECT forward proxy and the O(1) weighted round-robin behaviour against your own traffic, because the README states the capabilities but does not document their limits.

Frequently asked questions

What is Tengine?

Tengine is a high-performance web server and reverse proxy originated by Taobao, described in its README as 100% compatible with nginx and inheriting all features of nginx-1.31.5. It adds HTTP/3, Kubernetes Ingress support, active upstream health checks and NTLS/TLCP with the SM2, SM3 and SM4 algorithms.

How does Tengine compare with OpenResty?

Both support Lua, but Tengine treats Lua as one extension among many, alongside C-level mechanisms such as the input body filter for writing Web Application Firewalls and the module system inherited from nginx. OpenResty is organised around Lua and its own module ecosystem.

How do I install Tengine with Docker?

The README publishes multi-arch images on every release, with a Debian flavour and a smaller Alpine flavour, pulled from ghcr.io/alibaba/tengine:latest. The server runs as /usr/sbin/tengine with /etc/tengine/tengine.conf, and additional server blocks go into /etc/tengine/conf.d/.

Does Tengine have a Kubernetes Ingress controller?

Yes. The README attributes dynamic configuration of servers, locations and upstreams without reloading or restarting worker processes, along with header, cookie and query-parameter based routing and failover by response status code, to tengine-ingress, the Kubernetes Ingress controller for Tengine.

What licence does Tengine use?

The repository licence is BSD-2-Clause. The Dockerfile names Tongsuo, xquic and LuaJIT as separately compiled third-party dependencies, so their own licences apply to those components when you redistribute an image or package.

Official sources

  1. alibaba/tengine on GitHub
  2. License: BSD-2-Clause
  3. Project website
  4. README
  5. Releases
For maintainers

Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/alibaba-tengine.svg)](https://hysenlabs.com/projects/alibaba-tengine)
Community notes

Community notes