Using Replication Filters Deliberately: Replicating Only What Matters
AI generated
InnoDB
SQL
MySQL · Replication · Filters
Replication Filters
using them deliberately to replicate only what matters

Not every replica needs the full dataset of the source. Replication filters make it possible to build reporting replicas without sensitive customer data, or multi-store setups with cleanly separated databases, but they come with their own pitfalls the moment a filter needs to change after the fact.

11 min read Reporting Multi-Store

1. Why replication filters: reporting replicas and multi-store setups

A full replica by default replicates every database and every table from the source, regardless of whether the target system actually needs that data at all. For a reporting system that only accesses aggregated order and product data, that means unnecessarily transferred data volume and, far more critically, an unnecessary copy of sensitive tables such as customer addresses or payment data sitting on a system that has no real need to access them.

Replication filters address exactly this: they let you define, at the database or table level, which parts of the binlog actually get applied on a given replica. For multi-store environments with a separate database per tenant, this opens up a second, equally practical use case: a replica can be limited to just a single tenant's database, for example for a dedicated, tenant-specific analytics or support server.

2. Statement-based filters at the instance level: replicate-do-db and replicate-ignore-db

The simplest filter level operates on entire databases: replicate-do-db limits replication to explicitly named databases, replicate-ignore-db excludes named databases and replicates everything else. Under statement-based replication, the server evaluates the currently active database set via USE, not the tables actually touched inside the statement.

This exact evaluation logic is a common source of trouble with cross-database statements: an UPDATE reporting_db.summary SET ... WHERE EXISTS (SELECT 1 FROM shop_db.orders ...) gets filtered purely based on the database active via USE, even when the statement itself touches a different, supposedly excluded database. Anyone working with cross-database queries like this should use database-level filters with extra caution or fall back to table-based filters instead.


# In the replica's configuration file (mysqld section)
replicate-do-db = shop_db
replicate-ignore-db = shop_db_reporting_internal

3. Table level: replicate-do-table and wildcard filters

Filters at the table level operate far more precisely: replicate-do-table and replicate-ignore-table target individual, fully named tables, while replicate-wild-do-table and replicate-wild-ignore-table allow wildcard patterns with % and _, for example to exclude every table matching a given prefix at once. For a reporting replica, this lets you exclude individual sensitive tables without pulling the entire database into a database-level filter.

A typical pattern for a Magento-adjacent reporting replica explicitly excludes tables carrying personal or payment-related data, while keeping the bulk of the schema available for analysis. It matters that filtering still happens at the level of whole tables, native MySQL replication filtering does not support column-level filtering, for example to exclude only specific fields of a customer table.


replicate-wild-ignore-table = shop_db.customer_entity%
replicate-wild-ignore-table = shop_db.sales_order_payment%
replicate-wild-ignore-table = shop_db.customer_address_entity%

4. How MySQL evaluates the filter order

When both do and ignore rules are active at the same time, the server evaluates do rules first: if at least one replicate-do-table or replicate-wild-do-table rule exists, an event only gets replicated if it is explicitly covered by one of those rules, regardless of any additionally defined ignore rules. Only once no do rule matches at all do the ignore rules come into play, excluding explicitly named patterns from an otherwise complete replication.

This order often clashes with the intuitive expectation that do and ignore rules cooperate as equals. In practice this means: whoever accidentally sets both a do rule for shop_db and an ignore rule for a single table inside that database needs to understand precisely that the do rule takes precedence, and the ignore rule stays without effect unless it is also covered by a matching do rule.

5. Specifics of row-based filters

Under row-based replication, the default binlog format in most production environments since MySQL 5.7, events are not filtered based on the SQL text but based on the target table, which is explicitly encoded in every row event. That makes filtering noticeably more robust against cross-database statements, because the actually affected table is known independently of the calling SQL context, unlike the statement-based evaluation through the active USE database.

One important difference still applies though: replicate-do-db and replicate-ignore-db still evaluate the database that the target table resides in for row-based events, not the session database active at execution time. For environments running row format, this behavior is in practice more intuitive and predictable than its statement-based counterpart, which is why row format is also the more robust choice from a filtering standpoint.

6. CHANGE REPLICATION FILTER as a modern, dynamic alternative

Besides static configuration through the server config file, CHANGE REPLICATION FILTER lets you set filter rules at runtime, without restarting the server. The replication thread has to be stopped for this, but a full restart of the mysqld process is not required, which is a real operational advantage in environments with strict availability requirements.

This dynamic variant works well for temporary adjustments, for example to briefly exclude an additional table from a filter during a migration. For permanent filter rules, the static configuration file remains the more robust choice, since CHANGE REPLICATION FILTER falls back to the values in the config file after a server restart unless combined with a PERSIST option.


STOP REPLICA;
CHANGE REPLICATION FILTER
  REPLICATE_WILD_IGNORE_TABLE = ('shop_db.customer_entity%', 'shop_db.sales_order_payment%');
START REPLICA;

SHOW REPLICA STATUS\G

7. Pitfalls when changing a filter after the fact

The biggest practical pitfall arises when a filter changes after the replica has already been running with the old filter for an extended period. If, for example, a previously excluded table gets added into replication later on, the replica holds no historical data for that table, only the changes from the moment the filter changed onward, resulting in an inconsistent, partially empty dataset that looks unremarkable at first glance.

The only reliable fix in that case is a full resync of the replica for the affected table, usually through a targeted data export from the source or a complete replica rebuild from a current backup. Under GTID-based replication, this gets further complicated by the fact that gtid_purged and the replica's already known GTID set do not automatically line up with the new filter configuration, which is why a clean resync usually remains the only viable path, rather than trying to incrementally close the gap.

8. Use case multi-store: separate databases per tenant

In multi-store architectures with a dedicated database per tenant, replication filters let you build dedicated replicas that hold only a single tenant's data, for example for a tenant-specific support access or an isolated test environment with production-like but privacy-restricted data. Scoping replicate-do-db to a specific tenant database implements this scenario without any additional infrastructure such as separate ETL pipelines.

It matters that shared, cross-tenant reference data, where it exists, either gets included in the filter rule as well or gets deliberately documented as a known limitation, since a too-narrowly scoped database filter would otherwise break functionality that depends on that shared data, without the resulting error obviously pointing back at replication filtering at first glance.

9. Use case reporting replica: deliberately excluding sensitive tables

For a reporting replica feeding business intelligence tools or data warehouse load processes, the GDPR angle is the central driver behind replication filters: tables carrying direct personal data, such as customer addresses, payment tokens, or contact history, should not physically exist there in the first place, rather than being secured after the fact purely through access rights. A consistently filtered replica structurally reduces both the attack surface and the blast radius of a possible data leak, independent of how careful access control on the target system happens to be.

In practice it pays to document the list of sensitive tables centrally and actively check, with every new Magento module installation, whether new, potentially sensitive tables have appeared that need to be added to the existing filter configuration. That upkeep is a recurring but necessary effort, easily forgotten without a fixed process, until a new table quietly ends up on the reporting replica.

Filter Type Scope Evaluated Against Typical Use Case
replicate-do-db Entire database Active USE database (statement) or target table (row) Multi-store replica per tenant
replicate-ignore-db Entire database Active USE database (statement) or target table (row) Excluding an internal reporting database
replicate-do-table Single table Full table name Replicating only explicitly needed tables
replicate-wild-ignore-table Table pattern Wildcard pattern with % and _ Excluding whole table groups like sales_order_payment%
CHANGE REPLICATION FILTER Any, dynamic At runtime, no restart needed Temporary adjustment during a migration

Mironsoft

Database performance, index tuning, and Magento DB optimization

A Magento shop suffering from slow database queries?

We analyze MySQL databases for performance bottlenecks, optimize indexes and queries with purpose, and set up backup and replication strategies that actually work when it counts.

Performance Audit

Systematically investigate the slow query log and explain plans for bottlenecks.

Index Optimization

Build indexes with purpose for the shop's actual query load.

Backup Strategy

Set up reliable backup and restore processes for production Magento databases.

10. Summary

Replication Filters: Key Facts at a Glance

Core Idea

Replication filters restrict which databases or tables a replica pulls from the source's binlog in the first place.

Evaluation Rule

If at least one do rule exists, it takes precedence over ignore rules, which often clashes with the intuitive expectation.

Biggest Pitfall

A table added later contains no historical data, only a full resync closes that gap cleanly.

Typical Benefit

Reporting replicas without sensitive tables and multi-store replicas scoped to a single tenant database can be built without an additional ETL pipeline.

11. FAQ: Replication Filters: Key Facts at a Glance

1What is the difference between replicate-do-db and replicate-do-table?
replicate-do-db operates on entire databases and, under statement-based replication, evaluates the active USE database. replicate-do-table targets individual, fully named tables and is therefore far more precise for targeted exclusions.
2Why are database-level filters risky with cross-database statements?
Because under statement-based replication only the database active via USE is evaluated, not the tables actually touched inside the statement. A cross-database access can therefore slip through unfiltered or get blocked incorrectly.
3What happens if I set both do and ignore rules at the same time?
If at least one do rule exists, it takes precedence: only explicitly covered objects get replicated, ignore rules only kick in once no do rule is defined at all. This order often clashes with intuitive expectations and should be tested before going to production.
4Is row-based filtering more robust than statement-based?
Yes, since the target table is encoded directly in the event under row format, independent of the calling SQL context. That makes filtering noticeably more predictable under cross-database access than statement-based replication.
5Can I change filters without restarting the server?
Yes, CHANGE REPLICATION FILTER lets you set rules at runtime, the replication thread just needs to be stopped briefly. For permanent rules, the static configuration file remains the more robust choice.
6What happens if I later include a table that was previously excluded?
The replica only receives changes from the moment the filter change took effect, no historical data. The only reliable fix is a full resync of that table or of the entire replica.
7Can replication filters apply to individual columns?
No, native MySQL replication filters operate exclusively at the database or table level. Column-level filtering requires additional tools outside the built-in mechanisms, such as a custom ETL process.
8Are replication filters suitable for GDPR-compliant reporting replicas?
Yes, they are a sensible structural building block, since sensitive tables never physically exist there in the first place, rather than being protected purely through access rights. They do not replace a full data protection impact assessment though.
9Do replication filters affect GTID sets?
A replica's GTID set still includes every transaction, filtered or not, since certification happens at the transaction level, not the table level. After a later filter change, that GTID set does not automatically align with a clean resync though.
10Do I strictly need filters for a multi-store setup with separate databases?
Not strictly, but it is the most pragmatic way to build a tenant-specific replica without additional ETL infrastructure. The same effect could alternatively only be achieved through separate, full replica instances at a noticeably higher resource cost.