Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/afraid-lobsters-hang.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@wpengine/wpgraphql-logging-wordpress-plugin": patch
---

chore: Added data management for the logging plugin.
130 changes: 129 additions & 1 deletion plugins/wpgraphql-logging/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,9 @@ wpgraphql-logging/
│ ├── Admin/ # Admin settings, menu, and settings page logic
│ ├── Settings/ # Admin settings functionality for displaying and saving data.
│ ├── Events/ # Event logging, pub/sub event manager for extending the logging.
│ ├── Logging/ # Logging logic, logger service, Monolog handlers & processors
│ ├── Logger/ # Logging logic, logger service, Monolog handlers & processors
│ ├── Rules/ # Rule Management on whether we log a query
│ ├── Scheduler/ # Automated data cleanup and maintenance tasks
│ ├── Plugin.php # Main plugin class (entry point)
│ └── Autoload.php # PSR-4 autoloader
├── tests/ # All test suites
Expand Down Expand Up @@ -119,6 +121,12 @@ wpgraphql-logging/
- **Monolog-powered logging pipeline**
- Default handler: stores logs in a WordPress table (`{$wpdb->prefix}wpgraphql_logging`).

- **Automated data management**
- **Daily cleanup scheduler**: Automatically removes old logs based on retention settings.
- **Configurable retention period**: Set how many days to keep log data (default: 30 days).
- **Manual cleanup**: Admin interface to trigger immediate cleanup of old logs.
- **Data sanitization**: Remove sensitive fields from logged data for privacy compliance.

- **Simple developer API**
- `Plugin::on()` to subscribe, `Plugin::emit()` to publish, `Plugin::transform()` to modify payloads.

Expand All @@ -127,6 +135,126 @@ wpgraphql-logging/

---

## Data Sanitization

WPGraphQL Logging includes robust data sanitization capabilities to help you protect sensitive information while maintaining useful logs for debugging and monitoring. The sanitization system allows you to automatically clean, anonymize, or remove sensitive fields from log records before they are stored.

### Why Data Sanitization Matters

When logging GraphQL requests, context data often contains sensitive information such as:
- User authentication tokens
- Personal identification information (PII)
- Password fields
- Session data
- Internal system information

Data sanitization ensures compliance with privacy regulations (GDPR, CCPA) and security best practices while preserving the debugging value of your logs.

### Sanitization Methods

The plugin offers two sanitization approaches:

#### 1. Recommended Rules (Default)
Pre-configured rules that automatically sanitize common WordPress and WPGraphQL sensitive fields:
- `request.app_context.viewer.data` - User data object
- `request.app_context.viewer.allcaps` - User capabilities
- `request.app_context.viewer.cap_key` - Capability keys
- `request.app_context.viewer.caps` - User capability array

#### 2. Custom Rules
Define your own sanitization rules using dot notation to target specific fields:

**Field Path Examples:**
```
variables.password
request.headers.authorization
user.email
variables.input.creditCard
```

### Sanitization Actions

For each field, you can choose from three sanitization actions:

| Action | Description | Example |
|--------|-------------|---------|
| **Remove** | Completely removes the field from logs | `password: "secret123"` → *field removed* |
| **Anonymize** | Replaces value with `***` | `email: "user@example.com"` → `email: "***"` |
| **Truncate** | Limits string length to 47 characters + `...` | `longText: "Very long text..."` → `longText: "Very long text that gets cut off here and mo..."` |

### Configuration

Enable and configure data sanitization through the WordPress admin:

1. Navigate to **GraphQL Logging → Settings**
2. Click the **Data Management** tab
3. Enable **Data Sanitization**
4. Choose your sanitization method:
- **Recommended**: Uses pre-configured rules for common sensitive fields
- **Custom**: Define your own field-specific rules

#### Custom Configuration Fields

When using custom rules, configure the following fields:

- **Fields to Remove**: Comma-separated list of field paths to completely remove
- **Fields to Anonymize**: Comma-separated list of field paths to replace with `***`
- **Fields to Truncate**: Comma-separated list of field paths to limit length

**Example Configuration:**
```
Remove: variables.password, request.headers.authorization
Anonymize: user.email, variables.input.personalInfo
Truncate: query, variables.input.description
```

### Developer Hooks

Customize sanitization behavior using WordPress filters:

```php
// Enable/disable sanitization programmatically
add_filter( 'wpgraphql_logging_data_sanitization_enabled', function( $enabled ) {
return current_user_can( 'manage_options' ) ? false : $enabled;
});

// Modify recommended rules
add_filter( 'wpgraphql_logging_data_sanitization_recommended_rules', function( $rules ) {
$rules['custom.sensitive.field'] = 'remove';
return $rules;
});

// Modify all sanitization rules
add_filter( 'wpgraphql_logging_data_sanitization_rules', function( $rules ) {
// Add additional rules or modify existing ones
$rules['request.custom_header'] = 'anonymize';
return $rules;
});

// Modify the final log record after sanitization
add_filter( 'wpgraphql_logging_data_sanitization_record', function( $record ) {
// Additional processing after sanitization
return $record;
});
```

### Performance Considerations

- Sanitization runs on every log record when enabled
- Complex nested field paths may impact performance on high-traffic sites
- Consider using recommended rules for optimal performance
- Test custom rules thoroughly to ensure they target the intended fields

### Security Best Practices

1. **Review logs regularly** to ensure sanitization is working as expected
2. **Test field paths** in a development environment before applying to production
3. **Use remove over anonymize** for highly sensitive data
4. **Monitor performance impact** when implementing extensive custom rules
5. **Keep rules updated** as your GraphQL schema evolves

---

## Usage

WPGraphQL Logging Plugin is highly configurable and extendable and built with developers in mind to allow them to modify, change or add data, loggers etc to this plugin. Please read the docs below:
Expand Down
Original file line number Diff line number Diff line change
@@ -1,14 +1,15 @@
settings_page_wpgraphql-logging #poststuff .postbox .inside h2 {
.settings_page_wpgraphql-logging #poststuff .postbox .inside h2 {
font-size: 1.3em;
font-weight: 600;
padding-left: 0;
}


.form-table td input[type="number"],
.form-table td input[type="text"] {
width: calc(99% - 24px);
display: inline-block;
}

.form-table td select {
width: calc(99% - 24px);
display: inline-block;
Expand Down Expand Up @@ -47,12 +48,11 @@ settings_page_wpgraphql-logging #poststuff .postbox .inside h2 {
.wpgraphql-logging-tooltip .tooltip-text::after {
content: "";
position: absolute;
top: 0;
top: 50%;
left: -10px;
border-width: 6px;
border-style: solid;
border-color: transparent #1d2327 transparent transparent;
top: 50%;
transform: translateY(-50%);
}

Expand All @@ -71,16 +71,19 @@ settings_page_wpgraphql-logging #poststuff .postbox .inside h2 {
.wpgraphql-logging-docs ul li:before {
content: url(../../icons/doc.svg);
height: 1em;
width: 0.5em;
margin-left: -29px;
margin-top: -2px;
position: absolute;
width: 0.5em;
}


.wpgraphql-logging-feature-list {
list-style-type: disc;
font-size: 1.1em;
margin-left: 30px;
padding-bottom: 16px;
}

.wpgraphql-logging-custom:not(.block) {
display: none;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
document.addEventListener('DOMContentLoaded', function() {
const sanitizationMethodSelect = document.querySelector("#data_sanitization_method");
if (!sanitizationMethodSelect) {
return;
}

function toggleCustomFields() {
const isCustom = sanitizationMethodSelect.value === 'custom';
const customElements = document.querySelectorAll('.wpgraphql-logging-custom');

customElements.forEach((el) => {
if (isCustom) {
el.classList.add('block');
} else {
el.classList.remove('block');
}
});
}

toggleCustomFields();
sanitizationMethodSelect.addEventListener('change', toggleCustomFields);
});
1 change: 1 addition & 0 deletions plugins/wpgraphql-logging/composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@
"johnpbloch/wordpress-core": "^6.8",
"lucatume/wp-browser": "^4.0",
"mockery/mockery": "^1.5",
"php-stubs/wordpress-stubs": "^6.8",
"phpcompatibility/php-compatibility": "dev-develop as 9.99.99",
"phpcompatibility/phpcompatibility-wp": "^2.0",
"phpstan/phpstan-strict-rules": "^2.0",
Expand Down
Loading