---
title: "Migrating from WSO2 to Zuplo: Component Mapping, Architecture Translation, and Step-by-Step Guide"
description: "A practical guide for teams migrating from WSO2 API Manager to Zuplo, covering component mapping, mediation sequence translation, and a phased migration plan."
canonicalUrl: "https://zuplo.com/learning-center/migrating-from-wso2-to-zuplo"
pageType: "learning-center"
authors: "nate"
tags: "API Gateway, Tutorial"
image: "https://zuplo.com/og?text=Migrating%20from%20WSO2%20to%20Zuplo"
---
WSO2 API Manager is a comprehensive enterprise API management platform, but its
multi-component Java architecture comes with significant operational overhead.
If your team is evaluating whether to upgrade WSO2 versions, move off
self-hosted infrastructure, or transition to a fully managed platform, this
guide walks you through every step of migrating from WSO2 to Zuplo.

## Table of Contents

1. [Why Teams Migrate from WSO2](#why-teams-migrate-from-wso2)
2. [Architecture Comparison](#architecture-comparison)
3. [Component Mapping](#component-mapping)
4. [Translating WSO2 Configuration to Zuplo](#translating-wso2-configuration-to-zuplo)
5. [Mediation Sequence Translation](#mediation-sequence-translation)
6. [Authentication Migration](#authentication-migration)
7. [Rate Limiting and Traffic Management Migration](#rate-limiting-and-traffic-management-migration)
8. [API Key and Subscription Migration](#api-key-and-subscription-migration)
9. [Developer Portal Migration](#developer-portal-migration)
10. [Analytics and Monitoring Migration](#analytics-and-monitoring-migration)
11. [CI/CD and GitOps](#cicd-and-gitops)
12. [Step-by-Step Migration Playbook](#step-by-step-migration-playbook)
13. [Infrastructure Savings Analysis](#infrastructure-savings-analysis)
14. [Frequently Asked Questions](#frequently-asked-questions)
15. [Next Steps](#next-steps)

## Why Teams Migrate from WSO2

WSO2 API Manager is a capable platform with a strong enterprise pedigree, but
several pain points drive teams to look for alternatives:

- **Infrastructure complexity** — A production WSO2 deployment involves the API
  Gateway, Control Plane (Publisher, Developer Portal, Key Manager), Traffic
  Manager, and supporting databases. Each component requires Java runtime,
  Kubernetes orchestration, and careful tuning. Helm charts provided by WSO2 are
  not production-ready out of the box and need significant customization.
- **Java overhead** — WSO2 runs on the JVM. Every component requires Java heap
  tuning, garbage collection configuration, and JKS keystore management. Newer
  Java versions default to PKCS keystores, requiring explicit JKS configuration
  for WSO2 compatibility.
- **Opaque pricing** — WSO2's open-source version is free to download, but
  production-grade enterprise support, security patches, and advanced features
  require a commercial subscription with pricing that is not publicly listed.
  When you factor in infrastructure, DevOps time, and licensing, the total cost
  of ownership can be substantial.
- **Upgrade complexity** — Major version upgrades involve database migrations,
  component-by-component updates, mediation sequence compatibility testing, and
  Kubernetes manifest changes. Teams frequently defer upgrades because the
  process is time-consuming and risky.
- **Mediation sequences and XML** — WSO2's extensibility relies on XML-based
  mediation sequences using the Apache Synapse engine. Custom Java class
  mediators require building JAR files, deploying them to the Carbon framework,
  and managing class loading across gateway nodes.
- **Kubernetes mismatch** — WSO2's traditional VM-oriented architecture does not
  map cleanly to Kubernetes. Running WSO2 in containers introduces compatibility
  issues, fragmented configuration management, and observability gaps that
  require additional tooling to resolve.

## Architecture Comparison

Understanding the architectural differences helps you plan a clean migration.

### WSO2's Architecture

WSO2 API Manager uses a multi-component architecture organized into two main
planes:

**Control Plane (API Management Layer):**

- **API Publisher** — Web UI for creating, versioning, and publishing APIs.
  Manages API lifecycle states (Created, Published, Deprecated, Retired).
- **Developer Portal (API Store)** — A portal where developers discover APIs,
  create applications, subscribe to APIs, and manage their credentials.
- **Key Manager** — Handles OAuth 2.0 token generation, validation, and
  revocation. Manages client applications and their credentials. Connects to
  external identity providers via key manager connectors.
- **Service Catalog** — Registers backend services for API creation.

**Data Plane (Runtime Layer):**

- **API Gateway** — The Synapse-based runtime that intercepts API requests,
  applies security policies, enforces throttling, and proxies requests to
  backend services. Supports OAuth 2.0, JWT, API keys, Basic Auth, and mutual
  SSL.
- **Traffic Manager** — A real-time event processing engine that evaluates
  throttling policies. Uses a message broker to receive throttling events from
  gateway nodes and distribute decisions back.

**Integration Layer (Optional):**

- **Micro Integrator** — A lightweight integration runtime for service
  orchestration, message transformation, and protocol bridging.
- **Streaming Integrator** — A stream processing engine for real-time analytics
  and event-driven integrations.

All components run on Java and typically require Kubernetes (or VMs), databases
(MySQL, PostgreSQL, Oracle, or SQL Server), and shared file systems for certain
deployment patterns.

### Zuplo's Architecture

Zuplo takes a fundamentally different approach:

- **Edge-native deployment** — Your gateway runs across 300+ data centers
  worldwide automatically. There is no single-region deployment to manage or
  scale.
- **OpenAPI-native routing** — Routes are defined in a standard
  `routes.oas.json` file using the OpenAPI specification format, extended with
  `x-zuplo-route` for gateway behavior.
- **TypeScript policies** — Instead of XML mediation sequences and Java class
  mediators, you write policies in TypeScript with full IDE support, type
  safety, and access to npm packages. No compilation step, no JAR deployment, no
  class loading issues.
- **Git-native CI/CD** — Every configuration change is version-controlled. Push
  to GitHub, and your gateway deploys to the edge automatically.
- **Fully managed** — No Java runtime, no Kubernetes clusters, no databases, no
  JKS keystores. Zuplo handles all infrastructure, scaling, and updates.
- **Built-in developer portal** — Auto-generated from your OpenAPI spec, with
  API key management and API explorer included.

### Key Differences at a Glance

- **Infrastructure**: WSO2 requires Java + Kubernetes + databases + message
  brokers. Zuplo requires nothing — it is fully serverless.
- **Multi-region**: WSO2 requires deploying and synchronizing multiple gateway
  clusters. Zuplo deploys globally to 300+ locations by default.
- **Custom logic**: WSO2 uses XML mediation sequences and Java class mediators.
  Zuplo uses TypeScript with instant hot-reload.
- **Deployment model**: WSO2 uses Publisher UI, REST API, or Kubernetes
  Operator. Zuplo is Git-native — push and it deploys.
- **Developer portal**: WSO2's Developer Portal requires database setup and
  manual customization. Zuplo's portal is auto-generated from your OpenAPI spec.

## Component Mapping

The most common question during a WSO2 migration is: "What replaces each WSO2
component?" Here is a direct mapping:

### WSO2 Gateway → Zuplo API Gateway

The WSO2 Gateway's Synapse engine intercepts requests, applies mediation
sequences, and proxies to backend services. In Zuplo, this is replaced by the
edge-native gateway runtime. You define routes in `routes.oas.json` and attach
policies in `policies.json` — no Synapse engine, no XML, no Java.

### WSO2 Publisher → Zuplo OpenAPI-Driven Configuration

The WSO2 Publisher provides a UI for creating and managing APIs. In Zuplo, your
OpenAPI specification is the API definition. Import an existing spec, or write
one, and Zuplo creates routes, documentation, and validation automatically.
Changes go through Git pull requests rather than a web UI.

### WSO2 Developer Portal → Zuplo Auto-Generated Developer Portal

WSO2's Developer Portal (formerly API Store) requires database-backed storage
for applications, subscriptions, and developer accounts. Zuplo's
[developer portal](https://zuplo.com/docs/dev-portal/introduction) is
auto-generated from your OpenAPI spec and includes interactive documentation, an
API explorer, and self-serve API key management — with zero manual setup.

### WSO2 Traffic Manager → Zuplo Rate Limiting Policies

WSO2's Traffic Manager runs a Siddhi-based event processing engine to evaluate
throttling policies across gateway nodes. In Zuplo, rate limiting is a
[built-in policy](https://zuplo.com/docs/policies/rate-limit-inbound) configured
declaratively — no event processing engine, no message broker, no external
components.

### WSO2 Key Manager → Zuplo API Key Management

WSO2's Key Manager handles OAuth token generation and validation, integrating
with identity providers via key manager connectors. Zuplo provides a
[fully managed API key service](https://zuplo.com/docs/articles/api-key-management)
with global edge validation, consumer metadata, and a
[Developer API](https://zuplo.com/docs/articles/api-key-api) for programmatic
key management. For OAuth/JWT, Zuplo validates tokens from any OpenID-compliant
provider using the
[JWT Auth Policy](https://zuplo.com/docs/policies/open-id-jwt-auth-inbound).

### WSO2 Analytics → Zuplo Built-in Analytics

WSO2 Analytics requires deploying a separate analytics component with its own
database and dashboards. Zuplo includes built-in analytics dashboards and
supports direct integrations with
[OpenTelemetry](https://zuplo.com/docs/articles/opentelemetry), Datadog, New
Relic, and other observability platforms.

## Translating WSO2 Configuration to Zuplo

### WSO2 API Definition → Zuplo Routes

In WSO2, APIs are defined through the Publisher UI or REST API and stored in a
database. A typical WSO2 API has a context path, backend endpoint URL,
subscribed throttling policies, and attached mediation sequences.

In Zuplo, the equivalent lives in `routes.oas.json` — a standard OpenAPI file
extended with Zuplo-specific configuration:

```json
{
  "paths": {
    "/api/users/{userId}": {
      "get": {
        "summary": "Get User by ID",
        "x-zuplo-route": {
          "corsPolicy": "none",
          "handler": {
            "export": "urlRewriteHandler",
            "module": "$import(@zuplo/runtime)",
            "options": {
              "rewritePattern": "https://backend.example.com/users/${params.userId}"
            }
          },
          "policies": {
            "inbound": ["api-key-auth", "rate-limit"]
          }
        }
      }
    }
  }
}
```

The corresponding policies are defined in `policies.json`:

```json
{
  "policies": [
    {
      "name": "api-key-auth",
      "policyType": "api-key-inbound",
      "handler": {
        "export": "ApiKeyInboundPolicy",
        "module": "$import(@zuplo/runtime)"
      }
    },
    {
      "name": "rate-limit",
      "policyType": "rate-limit-inbound",
      "handler": {
        "export": "RateLimitInboundPolicy",
        "module": "$import(@zuplo/runtime)",
        "options": {
          "rateLimitBy": "user",
          "requestsAllowed": 100,
          "timeWindowMinutes": 1
        }
      }
    }
  ]
}
```

Key differences to note:

- **OpenAPI-native** — Zuplo routes are standard OpenAPI paths. You can import
  an existing OpenAPI spec and add `x-zuplo-route` extensions.
- **Policies replace mediation sequences** — Instead of XML sequences attached
  via the Publisher UI, you reference named policies in your route config.
- **Everything in Git** — Both `routes.oas.json` and `policies.json` are files
  in your repository. There is no separate database or Publisher UI to manage.

## Mediation Sequence Translation

WSO2's mediation sequences are XML-based configurations that run inside the
Synapse engine. If your team has custom mediation sequences or Java class
mediators, migrating them to Zuplo TypeScript policies is usually simpler than
you might expect. Zuplo's
[Custom Code Inbound Policy](https://zuplo.com/docs/policies/custom-code-inbound)
lets you write arbitrary request processing logic in TypeScript.

### WSO2 Mediation Sequence vs. Zuplo TypeScript Policy

Here is a side-by-side comparison of a header-injection mediation sequence:

**WSO2 (XML Mediation Sequence):**

```xml
<sequence name="AddCustomHeader" xmlns="http://ws.apache.org/ns/synapse">
  <header name="X-Custom-Header" value="my-value" scope="transport"/>
  <log level="custom">
    <property name="message" value="Custom header added"/>
  </log>
</sequence>
```

This XML sequence must be deployed through the Publisher UI, the Management
Console, or as a file in the `synapse-configs` directory.

**Zuplo (TypeScript):**

```typescript
import { ZuploContext, ZuploRequest } from "@zuplo/runtime";

export default async function (
  request: ZuploRequest,
  context: ZuploContext,
  options: { headerValue: string },
  policyName: string,
) {
  const newRequest = new ZuploRequest(request);
  newRequest.headers.set("X-Custom-Header", options.headerValue);
  context.log.info("Custom header added");
  return newRequest;
}
```

This TypeScript file goes in your `modules/` directory, is referenced in
`policies.json`, and deploys instantly when you push to Git. No XML, no Synapse
engine, no deployment artifacts.

### Java Class Mediator → Zuplo TypeScript Policy

WSO2 supports custom Java class mediators for complex logic. These require
building a JAR file, deploying it to the `lib` directory or Carbon framework,
and managing class loading across gateway nodes.

**WSO2 (Java Class Mediator):**

```java
package com.example.mediators;

import org.apache.synapse.MessageContext;
import org.apache.synapse.mediators.AbstractMediator;

public class EnrichPayloadMediator extends AbstractMediator {
    @Override
    public boolean mediate(MessageContext context) {
        String payload = context.getEnvelope().getBody().toString();
        // Parse and enrich payload
        org.json.JSONObject json = new org.json.JSONObject(payload);
        json.put("enriched", true);
        json.put("timestamp", System.currentTimeMillis());
        // Set modified payload back
        context.getEnvelope().getBody().getFirstElement()
            .setText(json.toString());
        return true;
    }
}
```

**Zuplo (TypeScript):**

```typescript
import { ZuploContext, ZuploRequest } from "@zuplo/runtime";

export default async function (
  request: ZuploRequest,
  context: ZuploContext,
  options: never,
  policyName: string,
) {
  const payload = await request.json();
  payload.enriched = true;
  payload.timestamp = Date.now();

  return new ZuploRequest(request, {
    body: JSON.stringify(payload),
  });
}
```

### Common Mediation Patterns and Their Zuplo Equivalents

**External service callout (WSO2 Call Mediator):**

WSO2 uses the `<call>` or `<callout>` mediator to invoke external services
during mediation.

**Zuplo equivalent:**

```typescript
import { ZuploContext, ZuploRequest } from "@zuplo/runtime";

export default async function (request: ZuploRequest, context: ZuploContext) {
  const token = request.headers.get("authorization");
  const resp = await fetch(`https://auth.example.com/validate?token=${token}`);

  if (!resp.ok) {
    return new Response("Unauthorized", { status: 401 });
  }

  return request;
}
```

**Conditional routing (WSO2 Filter Mediator):**

WSO2 uses the `<filter>` or `<switch>` mediator for conditional logic:

```xml
<filter xpath="get-property('transport', 'X-Client-Tier')='premium'">
  <then>
    <header name="X-Priority" value="high" scope="transport"/>
  </then>
  <else>
    <header name="X-Priority" value="normal" scope="transport"/>
  </else>
</filter>
```

**Zuplo equivalent:**

```typescript
import { ZuploContext, ZuploRequest } from "@zuplo/runtime";

export default async function (request: ZuploRequest, context: ZuploContext) {
  const clientTier = request.headers.get("x-client-tier");
  const priority = clientTier === "premium" ? "high" : "normal";

  const newRequest = new ZuploRequest(request);
  newRequest.headers.set("X-Priority", priority);
  return newRequest;
}
```

**Response transformation (WSO2 PayloadFactory Mediator):**

```xml
<payloadFactory media-type="json">
  <format>{"status": "$1", "data": $2}</format>
  <args>
    <arg evaluator="json" expression="$.status"/>
    <arg evaluator="json" expression="$.results"/>
  </args>
</payloadFactory>
```

**Zuplo equivalent (outbound policy):**

```typescript
import { ZuploContext, ZuploRequest } from "@zuplo/runtime";

export default async function (
  response: Response,
  request: ZuploRequest,
  context: ZuploContext,
) {
  const data = await response.json();
  const transformed = {
    status: data.status,
    data: data.results,
  };

  return new Response(JSON.stringify(transformed), {
    status: response.status,
    headers: response.headers,
  });
}
```

### Key Advantages of the TypeScript Approach

- **Full IDE support** — Autocomplete, type checking, and inline documentation
  in VS Code or any TypeScript-capable editor.
- **npm ecosystem** — Import any npm package for data validation, cryptography,
  or API calls.
- **Standard Web APIs** — Zuplo uses standard `Request`, `Response`, and
  `Headers` objects. If you know the Fetch API, you know how to write Zuplo
  policies.
- **Easier testing** — Unit test your policies like any TypeScript function. No
  need for a running Synapse engine or gateway instance.
- **No deployment artifacts** — WSO2 requires deploying JAR files for class
  mediators and CAR files for sequences. Zuplo deploys TypeScript from Git
  automatically.

## Authentication Migration

Authentication is typically the most critical part of any gateway migration.
Here is how to approach each WSO2 auth method.

### API Key Authentication

WSO2 supports API keys as a simpler authentication alternative, where keys are
generated per application through the Developer Portal.

Zuplo's
[API Key Authentication policy](https://zuplo.com/docs/policies/api-key-inbound)
provides a fully managed key service where you can:

1. Create consumers with metadata (plan tier, organization, etc.)
2. Issue API keys that are automatically validated at the edge — globally
3. Let developers self-manage their keys through the developer portal
4. Access consumer metadata in your policies via `request.user`

### OAuth 2.0 / JWT Authentication

WSO2's Key Manager component generates and validates OAuth 2.0 tokens. It can
act as a token issuer or integrate with external identity providers.

If your WSO2 setup uses an external identity provider (Auth0, Okta, Azure AD,
etc.) and WSO2 only validates tokens, migration is straightforward. Configure
Zuplo's
[JWT Auth Policy](https://zuplo.com/docs/policies/open-id-jwt-auth-inbound) with
the same provider settings:

```json
{
  "name": "jwt-auth",
  "policyType": "open-id-jwt-auth-inbound",
  "handler": {
    "export": "OpenIdJwtInboundPolicy",
    "module": "$import(@zuplo/runtime)",
    "options": {
      "issuer": "https://your-tenant.auth0.com/",
      "audience": "https://api.example.com/",
      "jwkUrl": "https://your-tenant.auth0.com/.well-known/jwks.json"
    }
  }
}
```

If you are using WSO2's Key Manager as your token issuer, you will need to move
token issuance to a dedicated identity provider like Auth0, Okta, or AWS
Cognito. Zuplo validates OAuth bearer tokens as JWTs but does not act as a token
issuer — this is by design, as dedicated identity providers handle this much
better.

Zuplo also has provider-specific policies for
[Auth0](https://zuplo.com/docs/policies/auth0-jwt-auth-inbound),
[Okta](https://zuplo.com/docs/policies/okta-jwt-auth-inbound),
[AWS Cognito](https://zuplo.com/docs/policies/cognito-jwt-auth-inbound), and
[Firebase](https://zuplo.com/docs/policies/firebase-jwt-inbound).

### Basic Authentication

WSO2 supports HTTP Basic authentication. Zuplo provides a
[Basic Auth Policy](https://zuplo.com/docs/policies/basic-auth-inbound) with
equivalent functionality.

### Mutual TLS (mTLS)

WSO2 supports mutual TLS for service-to-service authentication, configured
through JKS keystores and truststores. Zuplo provides an
[mTLS Auth Policy](https://zuplo.com/docs/policies/mtls-auth-inbound) for mutual
TLS authentication — without JKS keystore management.

## Rate Limiting and Traffic Management Migration

WSO2's Traffic Manager runs a Siddhi-based real-time event processing engine to
evaluate throttling policies. Throttling events are published from gateway nodes
to the Traffic Manager via a message broker, and throttling decisions are
distributed back. WSO2 supports multiple throttling levels: application-level,
subscription-level, API-level, and resource-level.

Zuplo's
[Rate Limiting policy](https://zuplo.com/docs/policies/rate-limit-inbound)
provides:

- **Per-user, per-IP, or per-key limiting** — Choose what attribute to rate
  limit by.
- **Custom bucket functions** — Write a TypeScript function to define custom
  rate limit grouping logic (e.g., rate limit by customer tier, organization, or
  any combination of request attributes).
- **No external dependencies** — Unlike WSO2's Traffic Manager with its event
  processing engine and message broker, Zuplo's rate limiter works out of the
  box without managing additional infrastructure.
- **Standard 429 responses** — Automatically returns `429 Too Many Requests`
  with appropriate `Retry-After` headers.

A typical rate limit configuration in Zuplo:

```json
{
  "name": "rate-limit",
  "policyType": "rate-limit-inbound",
  "handler": {
    "export": "RateLimitInboundPolicy",
    "module": "$import(@zuplo/runtime)",
    "options": {
      "rateLimitBy": "user",
      "requestsAllowed": 100,
      "timeWindowMinutes": 1
    }
  }
}
```

The biggest advantage here is eliminating the Traffic Manager entirely. No event
processing engine, no message broker, no inter-component communication to
configure and monitor.

## API Key and Subscription Migration

In WSO2, developers create applications in the Developer Portal, subscribe to
APIs, and receive consumer keys and secrets. These subscriptions tie together
the application, the API, and the throttling tier.

Zuplo uses a simpler model: consumers have API keys that grant access to your
gateway. Consumer metadata (plan tier, organization ID, etc.) is attached to the
consumer and available at runtime via `request.user.data`.

### Migrating Existing Consumers

To migrate your WSO2 subscribers to Zuplo, use the
[Zuplo Developer API](https://zuplo.com/docs/articles/api-key-api):

1. **Export your WSO2 subscribers** — Use the WSO2 Admin REST API to list
   applications and their subscriptions.
2. **Create Zuplo consumers** — For each WSO2 application, create a consumer in
   Zuplo with metadata that maps to the application's subscribed tier:

```bash
curl \
  https://dev.zuplo.com/v1/accounts/$ACCOUNT_NAME/key-buckets/$BUCKET_NAME/consumers?with-api-key=true \
  --request POST \
  --header "Content-type: application/json" \
  --header "Authorization: Bearer $ZAPI_KEY" \
  --data @- << EOF
{
  "name": "migrated-app-123",
  "description": "Migrated from WSO2 application",
  "metadata": {
    "plan": "gold",
    "organizationId": "org-456"
  },
  "tags": {
    "source": "wso2-migration",
    "wso2AppId": "app-123"
  }
}
EOF
```

3. **Distribute new API keys** — The response includes the new API key. Share it
   with the application owner or use Zuplo's
   [developer portal](https://zuplo.com/docs/dev-portal/introduction) for
   self-serve key management.

If you have many consumers, you can script the migration using the Zuplo
Developer API to bulk-create consumers programmatically.

## Developer Portal Migration

WSO2's Developer Portal (formerly API Store) is a separate web application that
requires database storage, manual theming, and configuration. Portal content,
developer applications, and API catalog data live in the shared database.
Customizing the portal involves editing Jaggery templates or React components
depending on your WSO2 version.

Zuplo's developer portal is built into the platform and
[auto-generated from your OpenAPI spec](https://zuplo.com/docs/dev-portal/introduction).
When you update your routes in `routes.oas.json`, the portal updates
automatically. Features include:

- **Automatic API documentation** — Generated directly from your OpenAPI
  specification, always in sync with your gateway.
- **API Explorer** — Developers can test your API directly from the docs.
- **Self-service API key management** — Consumers sign up, get keys, and manage
  them without your intervention.
- **Custom branding and pages** — Add custom Markdown, MDX, or React pages to
  your portal.
- **Custom domains** — Host your portal on `docs.yourcompany.com`.

There is no separate web application to deploy, no database to manage, and no
manual synchronization between your API definitions and your documentation.

## Analytics and Monitoring Migration

### WSO2's Analytics Architecture

WSO2 API Manager Analytics requires deploying a separate analytics component
(historically based on WSO2 Analytics Server or Choreo Analytics) with its own
database, dashboards, and event processing infrastructure. Setting up analytics
involves configuring event publishers in the gateway, provisioning an analytics
database, and deploying dashboard components.

### Zuplo's Built-in Analytics

Zuplo includes built-in analytics dashboards covering request volumes, error
rates, latency percentiles, and per-API-key usage — without any additional
components to deploy.

For teams that need to integrate with their existing monitoring stack, Zuplo
supports:

- **OpenTelemetry** — Export traces and logs to any OTLP-compatible backend
  (Honeycomb, Jaeger, Dynatrace, and more). See the
  [OpenTelemetry documentation](https://zuplo.com/docs/articles/opentelemetry)
  for setup details.
- **Datadog** — Direct log and metrics integration
- **New Relic** — Real-time log and metrics forwarding
- **Splunk** — Log streaming for enterprise SIEM workflows
- **Google Cloud Logging** — Direct GCP integration

These integrations are configured in your `zuplo.runtime.ts` file:

```typescript
import {
  RuntimeExtensions,
  DataDogLoggingPlugin,
  environment,
} from "@zuplo/runtime";

export function runtimeInit(runtime: RuntimeExtensions) {
  runtime.addPlugin(
    new DataDogLoggingPlugin({
      apiKey: environment.DATADOG_API_KEY,
      url: "https://http-intake.logs.datadoghq.com/api/v2/logs",
    }),
  );
}
```

The biggest win is eliminating a separate analytics deployment entirely. No
analytics server, no analytics database, no event publisher configuration.

## CI/CD and GitOps

### WSO2's Workflow

WSO2 offers several deployment approaches, each with trade-offs:

- **Publisher UI** — Point-and-click API creation and management through the web
  interface. Changes go directly to the database.
- **REST API (apictl)** — The `apictl` CLI tool supports importing and exporting
  APIs for CI/CD workflows. This provides some automation but requires managing
  API artifacts and environment-specific configurations separately.
- **Kubernetes Operator (APK)** — WSO2's newer API Platform for Kubernetes uses
  Custom Resource Definitions (CRDs) for Kubernetes-native management, but
  requires migrating from the traditional APIM architecture.

Even with `apictl`, there is always a synchronization step between your version
control system and the running gateway state. The database remains the source of
truth, not your Git repository.

### Zuplo's Workflow

Zuplo's deployment model is Git-native:

1. Your gateway configuration (`routes.oas.json`, `policies.json`, and custom
   TypeScript modules) lives in a GitHub repository
2. Push to a branch, and Zuplo automatically creates a preview deployment
3. Merge to main, and the production gateway updates across all 300+ edge
   locations
4. Every deployment is immutable and versioned — rollback by reverting a commit
5. Environment variables handle per-environment differences (staging vs.
   production)

There is no CLI sync tool, no operator to deploy, no database to keep in sync.
The Git repo _is_ the production state. For more details, see the
[source control documentation](https://zuplo.com/docs/articles/source-control).

## Step-by-Step Migration Playbook

A typical WSO2-to-Zuplo migration follows three phases:

### Phase 1: Assessment and Setup (Week 1)

**Inventory your WSO2 deployment:**

- List every published API, its context path, and backend endpoint URL
- Document custom mediation sequences (in-sequence, out-sequence,
  fault-sequence)
- Identify any Java class mediators and their JAR dependencies
- Export application subscriptions and their throttling tiers
- Note OAuth configurations and external identity provider integrations
- Document any WSO2 Micro Integrator dependencies

**Set up Zuplo:**

- Create a Zuplo account at [portal.zuplo.com](https://portal.zuplo.com)
- Connect your GitHub repository for
  [GitOps deployments](https://zuplo.com/docs/articles/source-control)
- Import your OpenAPI specs into `routes.oas.json`
- Configure authentication policies to match your WSO2 auth setup
- Set up rate limiting policies to mirror your WSO2 throttling tiers
- Add environment variables for backend URLs and secrets

### Phase 2: Custom Logic and Testing (Week 2)

- Migrate mediation sequences to TypeScript policies
- Translate Java class mediators to TypeScript
- Configure the developer portal
- Migrate API consumers using the
  [Zuplo Developer API](https://zuplo.com/docs/articles/api-key-api)
- Test all routes against your backend services
- Validate authentication flows end-to-end
- Run load tests to verify rate limiting behavior
- Configure logging and analytics integrations

### Phase 3: Cutover and Validation (Weeks 3–4)

- Run Zuplo in parallel alongside WSO2 (both receiving traffic)
- Compare response behavior between WSO2 and Zuplo
- Gradually shift traffic from WSO2 to Zuplo using DNS or a load balancer
- Monitor error rates, latency, and throughput
- Complete DNS cutover to Zuplo using
  [custom domains](https://zuplo.com/docs/articles/custom-domains)
- Decommission WSO2 infrastructure (Gateway, Control Plane, Traffic Manager,
  databases, Kubernetes resources)
- Update developer portal URLs and API documentation

For more detail on zero-downtime strategies, see our guide to
[migrating from self-hosted to managed API gateways](/learning-center/migrate-self-hosted-to-managed-api-gateway).

### Rollback Strategy

Because Zuplo deployments are Git-based, rollback is straightforward:

- **Configuration rollback** — Revert the Git commit and push. The previous
  gateway configuration deploys automatically.
- **DNS rollback** — If you kept WSO2 running during the parallel phase, switch
  DNS back to WSO2's endpoints.

## Infrastructure Savings Analysis

Migrating from WSO2 to Zuplo eliminates entire categories of infrastructure:

**Components you eliminate:**

- Java runtime (JDK) on every node
- Kubernetes cluster (or VMs) for Gateway, Control Plane, and Traffic Manager
- Relational database (MySQL/PostgreSQL/Oracle) for API metadata, subscriptions,
  and user data
- JKS keystores and truststore management
- Message broker for throttling events
- Analytics server and analytics database
- Load balancers in front of each component
- Monitoring and alerting for all of the above

**Operational tasks you eliminate:**

- Java heap tuning and GC optimization per component
- Kubernetes cluster scaling, node management, and Helm chart maintenance
- Database backups, migrations, and performance tuning
- JKS keystore rotation and Java version compatibility management
- WSO2 version upgrades (database migrations, mediation sequence compatibility,
  component-by-component updates)
- Security patching across all Java dependencies
- Log aggregation pipeline management

**What replaces all of this:**

A Zuplo account. Your team writes TypeScript, pushes to Git, and the API is live
at the edge. Zuplo handles infrastructure, scaling, security patches, global
distribution, and uptime — all included in
[transparent, publicly listed pricing](https://zuplo.com/pricing).

## Frequently Asked Questions

### How long does a WSO2-to-Zuplo migration take?

For most teams, a complete migration takes two to four weeks depending on the
number of custom mediation sequences and Java extensions. Teams using mostly
built-in WSO2 policies (API key auth, rate limiting, standard transforms) can
often complete the migration in under a week because these map directly to Zuplo
built-in policies.

### Do I need to change my backend services?

No. Zuplo proxies requests to your existing backends using the
[URL Rewrite handler](https://zuplo.com/docs/handlers/url-rewrite). Your backend
services do not need any changes — Zuplo forwards requests just like WSO2 does.

### Do WSO2 mediation sequences work on Zuplo?

No. WSO2 mediation sequences are XML-based configurations that run inside the
Synapse engine. Zuplo uses a completely different extensibility model based on
TypeScript policies. However, most mediation sequence functionality has a direct
Zuplo equivalent — either a built-in policy or a short TypeScript custom code
policy. The mediation sequence translation section above covers the most common
patterns.

### What replaces WSO2's Kubernetes and database requirements?

Nothing — that is the point. Zuplo is fully managed and serverless. Rate
limiting, API key storage, analytics, and developer portal hosting are all
handled by the platform without any external infrastructure dependencies.

### Can I run Zuplo alongside WSO2 during migration?

Yes. The recommended approach is to run both gateways in parallel during the
cutover phase, using DNS or a load balancer to gradually shift traffic from WSO2
to Zuplo.

### Is WSO2 API Manager really free to use?

WSO2 API Manager is open source under the Apache 2.0 license, so the software
itself is free. However, production deployments require significant
infrastructure investment — Java runtime, Kubernetes clusters, databases, load
balancers, and monitoring. WSO2 also offers a commercial subscription for
enterprise support, security patches, and updates, with pricing that is not
publicly listed. When you factor in infrastructure costs and DevOps time, the
total cost of ownership can be substantial.

### What about WSO2's integration capabilities via Micro Integrator?

WSO2's broader platform includes extensive integration capabilities via WSO2
Micro Integrator. Zuplo focuses on API gateway and management at the edge. If
you need complex backend integrations, you can use Zuplo for the API management
layer while keeping your integration logic in existing systems or dedicated
integration platforms.

## Next Steps

**Ready to migrate?**
[Sign up for a free Zuplo account](https://portal.zuplo.com) and follow the
[Getting Started Guide](https://zuplo.com/docs/articles/step-1-setup-basic-gateway)
to set up your first gateway in minutes.

For planning your migration:

- [Compare Zuplo and WSO2](https://zuplo.com/api-gateways/wso2-alternative-zuplo)
  — See a detailed feature-by-feature comparison.
- [Apigee Migration Guide](/learning-center/migrating-from-apigee-to-zuplo) — If
  you are also evaluating other enterprise API gateways, see how the migration
  process compares.
- [Policy Catalog](https://zuplo.com/docs/policies/overview) — Browse all
  available built-in policies.
- [Custom Policies Documentation](https://zuplo.com/docs/policies/custom-code-inbound)
  — Learn how to write your own TypeScript policies.