WL#17018: MRS Server Component - Implement Component Infrastructure

Affects: MySQL-Router-26.x   —   Status: Complete

BACKGROUND

The MySQL REST Service (MRS) was originally delivered as a plugin to MySQL Router, enabling RESTful access to MySQL databases through HTTP endpoints. While effective in larger, distributed deployments, this architecture requires a separate Router process to be installed, configured, and monitored even when MRS is the only feature needed.

This WorkLog addresses the first and foundational task of embedding MRS directly into the MySQL Server, eliminating the need for a separate Router instance in small or REST-only deployments.

MOTIVATION

Embedding the Router-based MRS stack as a native MySQL Server component enables:

  • Simplified deployment: REST is available out of the box with MySQL Server, no separate Router process needed.
  • Improved developer experience: Faster setup and prototyping with a single binary.
  • Lower Resource Usage: Especially important for embedded or containerized deployments.
  • Better Integration: Tight coupling with server lifecycle, configuration, logging, and security mechanisms (e.g., SSL, security context, privileges).

USER-STORIES

  • As a developer building REST-based applications, I want to run a single MySQL Server process that includes REST support, so that I can prototype and test quickly without setting up MySQL Router.

  • As a DBA, I want to expose selected REST endpoints from the server itself, without needing to deploy, monitor, and secure a separate Router process.

  • As a DBA, I want the REST API to be available directly from the MySQL Server, so that I can reduce runtime dependencies and simplify packaging.

SUMMARY

This WorkLog implements the foundational infrastructure for running the MySQL REST Service (MRS) as a native MySQL Server component.

It introduces a new component named component_mysql_rest_service, responsible for embedding and managing the Router-based MRS plugin stack directly within the server process.

The component is designed to handle the full lifecycle of the embedded MRS stack, including loading, configuration, execution, and shutdown, while ensuring tight integration with the MySQL Server's subsystems.

Key responsibilities include:

  • Registering the component with the server
  • Linking statically with the required MySQL Router libraries (IO, HTTP, Harness, MRS, etc.)
  • Setting up lifecycle hooks for component initialization and shutdown
  • Initializing and running the embedded Router plugin stack
  • Managing logging via a dedicated component log sink that integrates with the server's logging system
  • Preparing for security-context-based internal SQL execution, internal MRS account configuration for the metadata and data accounts, and other configuration needed
  • Verifying and coordinating access to MRS metadata

This work also includes the necessary refactoring of MySQL Router plugins into static libraries, to allow their use from within the server without relying on dynamic plugin loading. This requires adjustments to the Router's internal plugin management logic.

This WL lays the foundation for a new privilege level, MYSQL_REST_SERVICE_ADMIN, which is introduced in follow-up WL#17019 to control access to component-management interfaces such as UDFs.

This component lays the foundation for upcoming enhancements, such as:

  • System variables for runtime configuration of the component and MRS, including future resource-governance controls for externally facing HTTP traffic
  • UDFs to manage the service and query internal metadata
  • Status variables for observability
  • Support for REST-related SQL syntax extensions
  • Support for MySQL Architectures (InnoDB Cluster, ReplicaSet, ClusterSet)
  • Support for MySQL Architectures for MRS exclusive usage (no Router)
  • Support for Heatwave Service MySQL replicas.

These features will be delivered in follow-up worklogs as part of the broader MRS-Component initiative.

Instrumentation and Observability

In WL#17018, direct observability of the embedded Router/MRS runtime is limited. The component integrates with the MySQL server log, and operations performed through MySQL component services may still generate Performance Schema data indirectly. However, this WorkLog does not provide explicit Performance Schema instrumentation for the component's own internal runtime resources. In particular, the following internal entities are not instrumented and therefore will not appear in Performance Schema tables such as performance_schema.threads, mutex_instances, rwlock_instances, socket_instances, or file_instances:

  • The asynchronous startup thread used during component initialization
  • Router service threads (HTTP, listener, and worker threads)
  • Internal mutexes, condition variables, and file/socket descriptors created by the component

Such instrumentation is handled by the server and is outside the control of the REST Service component. Direct internal instrumentation is outside the scope of this WorkLog.

Functional Requirements

  • FR1: MySQL Server shall provide a native REST Service as an installable component named component_mysql_rest_service.

  • FR2: The component must be installable and uninstallable through standard SQL syntax using INSTALL COMPONENT and UNINSTALL COMPONENT.

  • FR3: Upon installation, the REST Service must automatically start and become operational without requiring user configuration.

    • FR3.1: The REST Service must only become operational when valid TLS configuration is available.
    • FR3.2: If TLS is disabled, unsupported, or misconfigured, the component must not expose the REST endpoint and must remain inactive with a clear error message.
    • FR3.3: INSTALL COMPONENT registers the component and initiates startup, but operational readiness may complete asynchronously. If asynchronous startup later fails, the component remains installed but inactive, and the failure is reported in the server log.
    • FR3.4: The REST Service must only become operational when the required MRS metadata, internal execution accounts, and internal security context can be accessed and validated successfully during startup.
    • FR3.5: If required MRS metadata is not ready, REST services must remain unavailable while the component logs the condition and retries until the metadata is ready or shutdown begins. Internal execution-account or security-context validation failures must abort asynchronous startup and be logged clearly.

    NOTE: Operational readiness is also observable through the mysql_rest_service.state status variable introduced by WL#17019. When that interface is available, administrators can check this status variable to determine whether the component reached READY without relying only on server logs or probing the REST endpoint.

  • FR4: The component shall integrate with the MySQL Server lifecycle, ensuring proper initialization during server startup and clean shutdown during server stop or component uninstallation.

    • FR4.1: On component uninstallation or server shutdown, the REST endpoint must stop accepting new HTTP requests.
    • FR4.2: Authenticated HTTP session state issued by the component does not survive component stop, uninstall, or restart. Session cookies and JWT-based sessions issued by the component become invalid once the component is no longer running.
    • FR4.3: Component uninstallation or server shutdown must be handled correctly even if asynchronous MRS startup has not completed or REST requests are active. The pending startup path must be cancelled or joined, the REST endpoint must not become available after shutdown begins, new HTTP work must stop, and partially initialized or active resources must be released safely.

    NOTE: Component shutdown or uninstallation does not guarantee graceful draining of in-flight REST requests. Active request handling, including SQL execution, may be interrupted as part of normal server/session cleanup.

  • FR5: The component must integrate with the MySQL Server logging system, ensuring all REST-related messages appear in the server log and obey configured verbosity levels.

  • FR6: The component must use and preserve the persistent MRS metadata stored in the mysql_rest_service_metadata schema, ensuring that REST service definitions and bootstrap state survive server restarts.

  • FR7: The component hosting model introduced by this WorkLog must be compatible with follow-up registration of component-specific system variables, status variables, and UDFs through standard MySQL Server component interfaces.

Non-Functional Requirements

  • NFR1: The component must comply with the MySQL Server component API conventions and lifecycle model.

  • NFR2: The component must not materially reduce server performance or availability when installed.

  • NFR3: The component must integrate with MySQL logging, configuration, and security frameworks.

  • NFR4: Initialization or runtime errors must produce clear, actionable log output.

  • NFR5: The component must be cross-platform compatible with all operating systems supported by MySQL.

Component Name

component_mysql_rest_service

Installation and Lifecycle

(Implements FR2, FR3, FR4, NFR1)

Prerequisites

Before INSTALL COMPONENT 'file://component_mysql_rest_service' is executed:

  • A MySQL Server instance must be installed, running, and reachable.
  • The installing user must have the privileges required to execute INSTALL COMPONENT and the bootstrap privileges described below.

For the REST Service to become operational:

  • The MySQL instance must be configured for MySQL REST Service support through the existing MRS setup path, such as MySQL Shell for VS Code or the MySQL Shell REST SQL extension.
  • That setup path must create or upgrade the mysql_rest_service_metadata schema and the predefined MRS roles required by the component.
  • The MRS metadata schema must be at a version supported by this component and usable by the component.
  • Valid MySQL Server TLS certificate and key configuration must be available.

The internal component execution accounts (mysql_mrs_metadata and mysql_mrs_data) do not need to be created manually before installation. The component creates missing accounts with their required provider role as their default role. Existing accounts are reused only if they already satisfy the validation requirements; incompatible accounts are not modified.

If the metadata schema is missing, incomplete, or unsupported, INSTALL COMPONENT may still register the component, but REST services remain unavailable while the component logs the condition and periodically rechecks the metadata. If required roles are missing after the metadata becomes ready, either internal execution account is unsuitable, or TLS/security-context initialization fails, asynchronous startup aborts and the component remains installed but inactive with a clear error in the server log.

The component is installed and uninstalled using standard SQL syntax:

INSTALL COMPONENT 'file://component_mysql_rest_service'; UNINSTALL COMPONENT 'file://component_mysql_rest_service';

Component Bootstrap SQL

During INSTALL COMPONENT, bootstrap SQL executes asynchronously in separate MySQL command-service/Srv_session-backed THDs. Their security contexts are resolved from the installing session's effective MySQL account identity (priv_user and priv_host). Bootstrap does not execute in the installer THD, as mysql.session, or as either internal MRS account.

The installer session's active roles are not inherited. In addition to the privilege required for INSTALL COMPONENT, the installing identity must have, either directly or through its default roles:

  • CREATE USER
  • authority to grant the predefined provider roles
  • the privileges required to read the MRS schema version and to SELECT, INSERT, and UPDATE MRS runtime-registration metadata

Each missing internal account is created by a single atomic CREATE USER ... DEFAULT ROLE ... ACCOUNT LOCK statement. The statement implicitly grants the provider role and makes it the default role; separate GRANT and SET DEFAULT ROLE statements are not issued. Existing accounts are validated but are not modified.

Install-time metadata bootstrap uses the installer-derived identity. During subsequent server startup, the internal accounts must already exist and metadata operations execute as mysql_mrs_metadata. Missing or invalid accounts cause startup to fail.

Binary Logging and Replication

The component does not disable sql_log_bin for bootstrap sessions. Successful account DDL and metadata DML therefore follow normal binary-log and GTID semantics. INSTALL COMPONENT itself is not written to the binary log.

Bootstrap is supported only on a writable source or primary. Account and metadata events may replicate normally, but replicas must not perform an independent concurrent bootstrap. After promotion, startup must be retried; the component reuses the replicated accounts and registers the promoted server.

The component uses server_uuid to locate its previous registration. Registration uniqueness is enforced by (address, router_name), so every Router or component instance must have a distinct registration identity. A conflict causes startup to fail. Concurrent bootstrap on multiple writable members is out of scope for this Worklog.

WL#17018 supports only a single active component-hosted MRS runtime, on the current writable source or primary. Before MRS is started on a promoted replica, the previous primary must be stopped or fenced. The component does not detect replication role changes, coordinate failover, or redirect REST traffic. HTTP connections, MRS sessions, JWT state, caches, and in-flight requests are local to an instance and are not transferred during promotion.

Failure and Retry

The component does not bypass read_only or super_read_only. If a required write is rejected, asynchronous startup aborts and the component remains installed but inactive. Only metadata-readiness polling is automatic; other failures require startup to be retried after the cause is corrected.

There is no transaction spanning both account-creation statements and the runtime-registration metadata write. A successful statement remains committed if a later statement fails. A retry validates and reuses existing accounts, creates missing accounts when an installation-time privileged context is available, and does not remove successfully created state.

Installation behaviour

  • Registers with the MySQL Server component framework.
  • Verifies that valid server SSL certificate and key material are available.
  • Initializes security-context-based support for internal SQL execution.
  • Initializes the embedded MRS stack (IO, HTTP, MRS Router libraries) and prepares the embedded REST listener on its default port.
  • Starts background threads required to run the REST backend.
  • Returns control immediately after startup begins; initialization is asynchronous and non-blocking.
  • Successful completion of INSTALL COMPONENT means the component was registered and startup was initiated, not that the REST endpoint is already operational.
  • Any initialization failure detected during the asynchronous startup path (e.g., TLS misconfiguration) is logged as an ERROR and the component remains installed but inactive.

Uninstallation behaviour

  • Stops accepting new HTTP requests and signals the embedded MRS backend and background threads to stop.
  • Does not preserve or gracefully drain active HTTP sessions or in-flight REST requests at the HTTP layer.
  • MRS/Router HTTP worker threads are not tied to a THD for their whole lifetime; they become tied to server execution only while SQL is executed through the MySQL command-service path.
  • In-flight SQL execution uses an Srv_session-backed THD and may be interrupted as part of normal server session/THD cancellation and cleanup.
  • The component must not forcibly terminate an MRS worker thread while SQL execution is active; active command-service/Srv_session state must be closed or released through normal server cleanup.
  • If asynchronous MRS startup is still in progress, cancels or joins the pending startup path before completing uninstallation.
  • Ensures the REST endpoint does not become available after uninstallation or shutdown has started.
  • Releases memory and deregisters services.
  • Does not drop metadata or internal accounts to preserve state across restarts.

    NOTE: The component framework calls deinit() on both UNINSTALL COMPONENT and server shutdown; explicit uninstall cannot be distinguished, so destructive cleanup must not occur.

Security Context Integration

The MRS Component uses MySQL security context services for internal SQL execution instead of storing internal account credentials in a keyring.

The component creates or locates dedicated internal MySQL account identities for metadata access and application-data execution, and creates corresponding security contexts for them without requiring passwords. When the backend needs to execute internal SQL, it attaches the appropriate security context to a THD for the duration of the operation: the metadata account for request-serving metadata operations, and the data account for application-data operations executed by the embedded MRS runtime.

Security-context properties:

  • No internal passwords need to be generated, stored, retrieved, or rotated by the component.
  • No keyring backend is required for component operation.
  • In component/embedded mode, internal MRS account credentials are not stored in a keyring.
  • The internal MRS accounts are used as authorization identities for internal execution and are not exposed as external credentials.
  • Internal SQL execution continues to use the privileges granted to those accounts through the standard MySQL role model.

User Management Model

(Supports FR6)

The MRS Component manages two internal MySQL accounts: one for metadata access and one for application-data execution. Each account is granted only the provider role required for its execution domain.

This user and role model matches the MySQL REST Service design and is consistent with the MRS implementation in MySQL Router.

Internal Accounts

  • Metadata Account: 'mysql_mrs_metadata'@'localhost'
  • Data Account: 'mysql_mrs_data'@'localhost'

These are fixed regular MySQL account identities owned by the MRS provisioning flow. The localhost host part is used instead of % as a defense-in-depth measure. ACCOUNT LOCK prevents normal client authentication; restricting the host additionally prevents these accounts from matching remote client connections if they are accidentally unlocked or otherwise misconfigured. Same-named accounts at other hosts are distinct and are not reused by the component. They are not built-in internal server accounts such as mysql.session or mysql.sys.

Purpose

The internal accounts are used exclusively by the MRS backend:

  • mysql_mrs_metadata is used to access MRS metadata in mysql_rest_service_metadata
  • mysql_mrs_data is used to execute limited SQL operations needed to serve REST endpoints

The accounts are not exposed externally and are not intended for use by any MySQL client.

Account Privileges

The component ensures both internal accounts exist and have the required provider role:

  • mysql_mrs_metadata is granted mysql_rest_service_meta_provider
  • mysql_mrs_data is granted mysql_rest_service_data_provider

At the account level, WL#17018 grants only the following role memberships to the internal accounts:

GRANT 'mysql_rest_service_meta_provider' TO 'mysql_mrs_metadata'@'localhost';
GRANT 'mysql_rest_service_data_provider' TO 'mysql_mrs_data'@'localhost';

When the component creates the accounts, the same provider roles are also set as default roles in the CREATE USER statements:

CREATE USER 'mysql_mrs_metadata'@'localhost'
  DEFAULT ROLE 'mysql_rest_service_meta_provider'
  ACCOUNT LOCK;

CREATE USER 'mysql_mrs_data'@'localhost'
  DEFAULT ROLE 'mysql_rest_service_data_provider'
  ACCOUNT LOCK;

No direct object privileges, dynamic privileges, administrative privileges, or GRANT OPTION are granted to these accounts by the component.

These accounts are used through the MySQL security context service rather than password-based login:

  • The internal accounts must not be usable for external MySQL client login.
  • When the component auto-creates either account, it creates a locked regular MySQL account used only as an ACL identity for security-context lookup.
  • The component does not generate, store, retrieve, rotate, or use passwords or externally usable authentication credentials for these accounts.
  • When either account already exists, the component validates that it is locked and not usable for external login before using it.
  • If an existing internal account is unlocked or otherwise usable for external login, startup fails with a clear error and requires administrative intervention.
  • The component creates the appropriate security context and attaches it to a THD when internal SQL execution is needed.

MRS Provider Roles

The component depends on two predefined SQL roles that encode the privilege model for REST metadata and REST application data access. These roles are created and owned by the MRS metadata schema installation; the authoritative SQL definitions are in the mysql_rest_service_metadata schema creation script. WL#17018 does not define or own those roles, but depends on them being present and uses them for internal execution.

mysql_rest_service_meta_provider

Access Level: Metadata Schema (Primarily Read, with Limited Runtime Bookkeeping Writes)

This predefined role is used by the MySQL Router/Server MRS component to identify the REST services that need to be served.

It grants the privileges required for the MRS backend to:

  • Read REST service definitions
  • Inspect metadata in the mysql_rest_service_metadata schema

It does not grant privileges on application tables.

The explicit privileges granted to this role are defined in the metadata schema Authorization section and include, at a high level:

  • SELECT on MRS metadata objects required to discover and serve REST services, including representative objects such as:
    • service
    • db_schema
    • db_object
    • auth_app
    • auth_vendor
    • service_has_auth_app
    • content_set
    • content_file
    • content_set_has_obj_def
    • router
    • router_status
    • router_session
    • router_general_log
  • SELECT on supporting views and helper metadata such as:
    • msm_schema_version
    • mrs_user_schema_version
    • object_fields_with_references
    • router_services
  • Metadata object names with the router prefix are retained for compatibility with the existing MRS metadata schema and Router-hosted MRS tooling. Renaming these objects is out of scope for WL#17018.
  • INSERT and/or UPDATE on selected metadata objects required for runtime operation, especially those related to:
    • MRS-managed users
    • roles and privileges
    • group and hierarchy mappings
    • router and session bookkeeping
  • EXECUTE on helper metadata routines such as:
    • table_columns_with_references
    • get_sequence_id

mysql_rest_service_data_provider

Access Level: Application Data Access

This predefined role is used by the MySQL Router/Server MRS component to read and write the application data that should be served by REST services.

When a REST endpoint has been defined, the required privileges to access the underlying database schema objects must be granted to the mysql_rest_service_data_provider role.

For REST views exposing a database table or view, the required privileges are granted automatically.

For REST procedures and REST functions, the EXECUTE privilege on the exposed routine is granted automatically.

If an exposed procedure or function accesses additional procedures or other schema objects, additional manual GRANT statements for mysql_rest_service_data_provider may still be required.

The explicit privileges granted to this role are defined in the metadata schema Authorization section and include, at a high level:

  • CREATE TEMPORARY TABLES on mysql_rest_service_metadata.
  • SELECT on selected metadata objects needed at runtime for authorization-related lookups, including representative objects such as:
    • mrs_user
    • mrs_user_hierarchy
    • mrs_user_group_hierarchy
  • EXECUTE on helper metadata routines such as:
    • get_sequence_id
  • Access to application schema objects exposed through REST endpoints:
    • for REST views exposing tables or views, required privileges are granted automatically;
    • for REST procedures and REST functions, EXECUTE on the exposed routine is granted automatically;
    • if nested procedures or other referenced schema objects are used, additional manual GRANT statements may be required.

The authentication and unauthenticated-access modes and their SQL execution identities are described in Authentication and Authorization.

Requests using the shared MRS execution identity, including MRS-vendor requests, OAuth2-vendor requests, requests to services configured for unauthenticated access, and MySQL Internal requests to non-passthrough services, execute SQL as mysql_mrs_data with the mysql_rest_service_data_provider role. MySQL-passthrough requests instead execute under the authenticated MySQL user's security context. The separation between per-request REST authorization and the privileges of this shared execution identity is described in Non-Passthrough Authorization Boundary.

Lifecycle & Recovery

  • The component does not drop the internal accounts or roles during stop, uninstall, shutdown, or restart; they remain available for later component startup.
  • If either internal account cannot be created or validated, either required provider role is unavailable, or the security context for either internal account cannot be created:
    • The component logs a clear ERROR
    • The REST backend does not start
    • Manual recovery is required

Privilege and Role Management for REST Accounts

The MRS Component does not create or manage MySQL accounts for REST clients.

For the built-in MRS authentication vendor, REST users are MRS-specific accounts managed by the REST Service rather than MySQL server accounts. Authentication is handled entirely within MRS using a custom SCRAM-SHA-256 challenge-response flow over HTTPS. The password is not stored in plaintext; instead, MRS stores the SCRAM authentication material in mysql_rest_service_metadata.mrs_user.auth_string, including the salt, iteration count, and stored key required to verify the user proof. These users are not mapped directly to MySQL accounts for request execution.

After successful authentication, the component issues a session token for the authenticated MRS user. Depending on the selected session type, this is either a session cookie or a JWT. When a JWT is used, it is signed using the component's runtime-generated in-memory JWT signing key and is used as a short-lived proof of authentication on subsequent REST requests.

REST users fall into one of three authentication models, each with a distinct privilege mapping:

  1. REST Users Authenticated via MySQL Internal Vendor

    • These users authenticate using a MySQL username and password.
    • The HTTP authentication scheme is HTTP Basic authentication over TLS:
    • the client sends an Authorization: Basic <base64(username:password)> header during authentication;
    • MRS decodes the credentials and verifies them using the MySQL Server authentication framework;
    • credentials are used only for authentication and are not persisted beyond the authentication/session-establishment flow.
    • This documents the existing MRS MySQL Internal authentication scheme; WL#17018 does not introduce a new authentication scheme for this vendor.

    For the MySQL Internal vendor, MySQL Server authenticates the account and MRS maps the resulting MySQL authorization identity to an MRS user through the configured authentication application and mysql_rest_service_metadata.mrs_user.vendor_user_id. MRS uses that user for REST authorization. passthroughDbUser affects only the identity used for SQL execution; it does not replace MRS REST authorization.

    For services configured for MySQL-passthrough mode (passthroughDbUser = true):

    • REST requests are executed internally using the authenticated MySQL user's security context.
    • The REST request is executed with the exact same privileges the MySQL user has via GRANTs.
    • No additional roles are assigned.
    • No privilege escalation is possible.
    • The MRS component does not modify or manage their privileges.

    For services not configured for MySQL-passthrough mode (passthroughDbUser = false):

    • MRS authorizes each request using the REST configuration and the roles and REST privileges assigned to the mapped MRS user.
    • The authenticated MySQL account's object privileges are not used for request execution.
    • After MRS authorization succeeds, SQL is executed through the internal MRS data account (mysql_mrs_data) using mysql_rest_service_data_provider.
    • Effective access is the intersection of the operation permitted by the REST configuration and the user's MRS privileges, and the SQL privileges granted to the Data Provider role.
  2. REST Users Authenticated via MRS Vendor

(MRS-managed REST accounts)

  • These users are MRS REST Service specific accounts stored in mysql_rest_service_metadata.mrs_user.
  • They are authenticated entirely within MRS using a custom SCRAM-SHA-256 challenge-response flow over HTTPS.
  • Passwords are not stored in plaintext; MRS stores the SCRAM authentication material in mrs_user.auth_string, including the salt, iteration count, and stored key.
  • They are not mapped to MySQL accounts.
  • After successful authentication, MRS issues either a session cookie or a JWT, depending on the session type.
  • MRS loads the user's assigned roles and REST privileges from MRS metadata.
  • These privileges determine which REST services, schemas, objects, and CRUD operations the user may access.
  • After MRS authorization succeeds, SQL is executed through the internal MRS data account (mysql_mrs_data) using mysql_rest_service_data_provider.

    1. REST Users Authenticated via OAuth2 Vendors
  • These users authenticate using tokens issued by a configured OAuth2 vendor.

  • They are not mapped to MySQL accounts.
  • The authenticated OAuth2 identity is resolved to an MRS user.
  • MRS loads that user's assigned roles and REST privileges from MRS metadata and applies the same service, schema, object, and CRUD checks used for MRS-vendor users.
  • After MRS authorization succeeds, SQL is executed through the internal MRS data account (mysql_mrs_data) using mysql_rest_service_data_provider.

Non-Passthrough Authorization Boundary

For services that are not configured for MySQL-passthrough mode, MRS must authorize each request against the REST configuration and metadata before executing application-data SQL for the requested operation. This authorization includes the requested REST service, resource, and operation, and the authenticated identity when one is present. Only an authorized REST operation may reach the server-side SQL execution path.

This follows the existing MRS authorization model described in MRS Authorization Management.

mysql_mrs_data and mysql_rest_service_data_provider are a shared execution identity and define the maximum SQL privilege envelope for non-passthrough requests. They do not enforce per-REST-user authorization. REST clients do not receive the credentials or security context of mysql_mrs_data and cannot submit raw SQL through the REST API.

All request-controlled input used to construct application-data SQL must be processed by MRS query builders so that it cannot alter the intended SQL structure or select a database object outside the authorized REST definition. Values must be encoded as SQL values, identifiers must be resolved against MRS metadata and quoted as identifiers, and structural elements such as operators must be selected from validated sets. MRS may use prepared statements or internally generated direct SQL, but it must not concatenate unvalidated client input or accept arbitrary client-supplied SQL fragments.

An SQL injection defect could bypass the MRS authorization boundary and exercise any SQL privilege available to mysql_mrs_data, including access broader than the compromised REST user's authorization. The provider role does not prevent such a bypass; its least-privilege grants limit the resulting impact. MySQL privilege checks still constrain execution to the grants of mysql_mrs_data, which, as provisioned by this WorkLog, has no administrative privileges or GRANT OPTION.

Security Properties

  • The component does not grant MySQL administrative privileges or GRANT OPTION to REST users, internal MRS accounts, or MRS provider roles as part of provisioning.
  • Effective SQL privileges are determined by the MySQL grants assigned to the execution identity: the authenticated MySQL user in passthrough mode, or mysql_mrs_data / mysql_rest_service_data_provider in non-passthrough mode.
  • The privilege guarantees in this WorkLog describe the grants created and used by MRS itself. They do not prevent a privileged administrator from changing grants on the internal MRS accounts or provider roles after provisioning.
  • The MRS component does not create MySQL accounts for REST clients.
  • MRS REST authorization is enforced independently of the SQL execution identity. For authenticated REST users, assigned MRS roles and REST privileges determine which services, schemas, objects, and CRUD operations each user may access.
  • For MRS and OAuth2 users, mysql_mrs_data and mysql_rest_service_data_provider define the shared SQL execution privileges after MRS authorization succeeds; they do not grant every REST user access to every endpoint.
  • JWTs issued by the built-in MRS authentication vendor are valid only until expiration or component/server restart.
  • This WorkLog does not provide persistent JWT signing-key storage, key rotation, or cross-instance/shared-secret validation.
  • MRS REST operations do not add privileges beyond those available to the selected execution identity and the configured REST metadata.
  • Role membership is fixed and cannot be changed by REST operations.

Auto-Bootstrapping and Configuration

(Implements FR3, FR6, NFR3)

When first installed, the component automatically initializes the embedded REST Service stack:

  • Embedded Router Subsystem Initialization:

    • Initializes the required embedded Router subsystems from the statically linked Router libraries (IO, HTTP, Routing, MRS).
  • Automatic Account Creation:

    • Creates or reuses the dedicated internal accounts mysql_mrs_metadata and mysql_mrs_data. These accounts are used by the REST Service to access metadata and application data through the MySQL security context service, without requiring password storage.
    • If mysql_mrs_metadata does not exist, the component creates it as locked/non-login-capable and grants mysql_rest_service_meta_provider.
    • If mysql_mrs_data does not exist, the component creates it as locked/non-login-capable and grants mysql_rest_service_data_provider.
    • If either account already exists, the component validates that it is suitable for MRS use, including that it is locked/non-login-capable and has the required role and privileges.
    • If an existing account is incompatible with the MRS requirements, the component must not silently repurpose it; startup fails with a clear error and requires administrative intervention.

      NOTE: These accounts are the internal accounts used by the REST Service to access metadata and application data: mysql_user.

  • Initial Startup Defaults:

    • In WL#17018, these values are startup defaults or values derived from existing MySQL server configuration.
    • User-facing configuration of these settings is introduced in follow-up WL#17019 through component system variables.
    • Initial HTTP listener port: 33443
    • This avoids the documented MySQL defaults already assigned to 33060 (mysqlx), 33061, and 33062
    • TLS is mandatory. The component uses the embedded Router TLS stack, with TLS 1.2 as the minimum allowed protocol version. Newer protocols, including TLS 1.3, are supported when available in that stack.
    • @@ssl_cert and @@ssl_key are used as startup defaults for the MRS HTTP listener. This provides certificate and key material for TLS initialization, but does not guarantee that REST clients trust the issuing CA or accept the certificate for the REST endpoint identity.
    • Deployments must ensure that the certificate is trusted by the intended REST clients and valid for the REST endpoint. Otherwise, an MRS-specific certificate and key can be configured through mysql_rest_service.ssl_cert and mysql_rest_service.ssl_key, introduced by WL#17019.
    • WL#17018 does not expose MRS-specific cipher-suite or key-exchange configuration. The MRS listener uses the embedded Router TLS defaults, and available algorithms, including future PQC-capable algorithms, depend on that stack.
    • Because the MRS listener owns a separate TLS context, a future WorkLog may expose independent MRS TLS-policy controls through component configuration without changing the MySQL protocol-channel policy. Such controls, including cipher-suite and key-exchange/PQC configuration, are outside WL#17018.
    • If valid TLS configuration is not available, the component does not start
    • Component-hosted MRS developer mode and any associated Server-facing configuration interface are outside the scope of this worklog pending separate design review. Existing Router-hosted MRS behavior is unchanged.
  • Metadata Bootstrap:

    • The component depends on the mysql_rest_service_metadata schema being installed and upgraded by the existing MRS metadata installation/upgrade path; WL#17018 does not create or version-manage that schema.
    • Within that existing schema, the component performs runtime bootstrap. It stores @@server_uuid in the router.attributes JSON and uses it to locate its previous registration. If found, the component updates that row by id; otherwise, it inserts a new row. server_uuid is an application-level lookup attribute and does not replace the table's UNIQUE(address, router_name) constraint. Both updates and inserts remain subject to that constraint, and a conflicting Router or component registration causes startup to fail.
    • If a new entry is inserted, the generated identifier obtained from last_insert_id() is cached in memory and reused throughout the lifecycle.

Runtime TLS Certificate Reload

The MySQL protocol channels and the MRS HTTP listener use separate TLS contexts. ALTER INSTANCE RELOAD TLS refreshes the MySQL protocol channels; it does not refresh the MRS listener.

In WL#17018, the MRS certificate and private key are read when the embedded HTTP runtime starts. Applying refreshed TLS material therefore requires an MRS runtime restart. When the lifecycle interfaces from WL#17019 are available, administrators can perform this restart with mysql_rest_service_restart(). The restart interrupts existing MRS connections and session state; invalid TLS material leaves MRS inactive and produces a clear error.

Dynamic certificate reload without an MRS restart is outside WL#17018 and will be handled separately. Component-hosted MRS will reuse that behavior once it is available. The reload path must support the embedded Router runtime and must not depend on standalone Router process infrastructure.

Connection Management & Lifecycle

(Implements FR3, FR6)

The shared MRS design includes an internal cache of outbound MySQL client connections for Router-hosted execution paths that use internal MySQL client connectivity. This section refers to those MySQL client connections, not to inbound HTTP client connections.

In this WorkLog, component-hosted metadata and application-data SQL execution uses the security-context-based execution path described above, attaching the appropriate security context to a THD rather than using MySQL client/network connections from this cache. Embedded command-service sessions are created on demand and closed when returned; they are not retained for reuse across requests.

Unlike metadata and application-data SQL execution, MySQL Internal credential verification uses normal Server authentication. MRS uses the password-capable mysql_command_services API. Setting MYSQL_COMMAND_PASSWORD selects a short-lived local Classic Protocol connection to the current mysqld. MRS queries CURRENT_USER() on that connection to obtain the canonical authorization identity. The connection is closed after verification and is not retained or governed by the mysql.cache.* configuration.

The component processes the shared MRS configuration during metadata refresh, but the mysql.cache.* values do not control embedded-session retention or limit active embedded sessions.

For MySQL-passthrough execution, passthroughDbUser.poolSize limits the number of simultaneously active embedded SQL sessions within an authenticated MRS session. Returned sessions are closed rather than retained idle.

Router-Hosted Comparison

The following cache structure and behavior apply to Router-hosted MRS. During Router/component coexistence, the settings continue to apply to the Router-hosted connection caches only.

The cache structure remains internal to the backend and is not exposed to REST users or external MySQL clients.

The cache configuration is stored in the mysql_rest_service_metadata.config table; the metadata stores configuration for the cache, not the live connections themselves:

CREATE TABLE IF NOT EXISTS mysql_rest_service_metadata.config (
  id TINYINT NOT NULL DEFAULT 1,
  service_enabled TINYINT NULL,
  data JSON NULL,
  PRIMARY KEY (id)
) ENGINE=InnoDB;

The data JSON document contains global configuration for the MRS Service, including connection cache limits.

Cache Structure

The connection-cache structure is divided into four independent caches. The following strings are JSON Pointer paths into the cache configuration document, and each one identifies a specific cache bucket:

  • /mysql/cache/metadata/ro_instances: read-only metadata cache
  • /mysql/cache/metadata/rw_instances: read-write metadata cache
  • /mysql/cache/userdata/ro_instances: read-only application-data cache
  • /mysql/cache/userdata/rw_instances: read-write application-data cache

Each cache operates independently and defines the backend cache layout for that domain.

Configuration Format

The config.data JSON document stores cache configuration under the mysql.cache object.

For this WorkLog, the relevant keys are:

  • mysql.cache.metadata.ro_instances: retained size of the read-only metadata cache
  • mysql.cache.metadata.rw_instances: retained size of the read-write metadata cache
  • mysql.cache.userdata.ro_instances: retained size of the read-only application-data cache
  • mysql.cache.userdata.rw_instances: retained size of the read-write application-data cache

Each value is an integer specifying the maximum number of cached entries retained for that cache bucket.

Example configuration stored in config.data:

{
  "mysql": {
    "cache": {
      "userdata": {
        "ro_instances": 10,
        "rw_instances": 5
      },
      "metadata": {
        "ro_instances": 1,
        "rw_instances": 1
      }
    }
  }
}

Another valid example:

{
  "mysql": {
    "cache": {
      "userdata": {
        "ro_instances": 2,
        "rw_instances": 1
      },
      "metadata": {
        "ro_instances": 1,
        "rw_instances": 1
      }
    }
  }
}
  • All values must be integers greater than or equal to 0
  • They represent the maximum number of entries retained by each connection cache
  • A value of 0 means that returned connections are not retained for that cache bucket; they are closed/discarded instead

These values do not configure timeouts, idle retention, or creation policy, only the maximum number of cached connections.

Cache Behavior

Each cache keeps at most N connections, where N is the configured value:

/mysql/cache/userdata/ro_instances = 10 -> keep up to 10 cached connections

When a connection is returned to the cache:

  • If the cache contains fewer than its configured limit: The returned connection is appended to the cache and may be reused later.
  • If the cache is already at its configured limit: The returned connection is not added to the cache and is closed/discarded immediately.

The cache itself is FIFO-ordered.

NOTE: Connections are opened on demand, not at Router startup.

Failure Handling

If a cached connection becomes invalid, because for example:

  • network broken
  • server restarted

Then:

  • MRS reuses cached connections optimistically
  • if cache reuse validation rejects a cached connection, MRS discards it
  • MRS may try another cached connection from the same cache bucket, if one is available
  • a new connection is created lazily only when no reusable cached connection is available
  • if the first DB operation detects a disconnect, MRS may reconnect that same session once through the existing CountedMySQLSession reconnect path
  • no global restart is required

Failures in cached connections never block the Router-hosted MRS runtime from continuing operation.

Shutdown

During component shutdown or uninstall:

  • The REST endpoint stops accepting new HTTP requests
  • The embedded runtime is signaled to stop without a graceful-drain guarantee for in-flight REST requests at the HTTP layer
  • MRS/Router HTTP worker threads are not required to be associated with a THD while accepting, parsing, or serializing requests
  • If an in-flight REST request is executing SQL, that execution uses the MySQL command-service path with an Srv_session-backed THD
  • Active SQL execution may be interrupted during shutdown or uninstall through normal server session/THD cancellation and cleanup
  • The component does not forcibly terminate an MRS worker thread while SQL execution is active; associated command-service/Srv_session state is closed or released through normal server cleanup
  • Existing authenticated HTTP session state is discarded.
  • MRS-issued session cookies and JWT-backed sessions become invalid
  • No multi-request transaction state is preserved across stop, uninstall, or restart
  • No idle embedded MySQL sessions or outbound MySQL client connections are retained
  • No database-session state is persisted
  • Metadata persists normally
  • On restart, embedded sessions are created on demand.

DoS Protection

(Supports FR3, FR5, NFR4)

The embedded MRS component includes DoS-relevant protections inherited from the embedded Router/MRS runtime, primarily authentication throttling and bounded worker-thread execution.

Because the component is exposed directly to end users over HTTP, control of externally triggered resource consumption is an important design concern. In this foundational WorkLog, the component embeds the current Router/MRS runtime behavior but does not yet introduce administrator-visible global limits for concurrent HTTP connections, HTTP request body size, or HTTP response body size. Those explicit HTTP-layer controls are introduced separately.

In this WorkLog, DoS-related protections are based on:

  • request throttling
  • authentication rate-limiting

Authentication Throttling (per Account and per Host)

Authentication attempts are subject to:

  • per-host throttling for all authentication vendors, keyed by the immediate client source address
  • per-account throttling for MySQL Internal and MRS vendor flows, keyed by the authentication application and presented account name before credential verification

OAuth2 vendor flows are subject to per-host throttling. WL#17018 does not apply the MRS per-account throttle to OAuth2 authentication flows.

The throttling configuration is stored in:

SELECT data FROM mysql_rest_service_metadata.config

under the JSON path: authentication.throttling

Configuration Model

Authentication-throttling configuration is stored as JSON in the data column of the mysql_rest_service_metadata.config table.

For this WorkLog:

  • configuration keys are interpreted relative to the authentication.throttling object
  • each parameter is optional
  • if a parameter is absent, the corresponding throttling check is not enforced
  • all parameter values are INTEGER
  • the embedded MRS runtime reads and applies this configuration from metadata

Configuration parameters

  • perAccount.minimumTimeBetweenRequestsInMs: Minimum delay required between authentication attempts
  • perAccount.maximumAttemptsPerMinute: Max allowed authentication attempts per minute
  • perHost.minimumTimeBetweenRequestsInMs: Minimum delay required between requests from the same host
  • perHost.maximumAttemptsPerMinute: Max allowed authentication attempts per minute
  • blockWhenAttemptsExceededInSeconds: Block duration after a throttling threshold is exceeded

All values are INTEGER and if a parameter is not set, that check is not enforced.

Future work: perHost.* throttling uses the immediate client source address visible to the embedded HTTP server. Deployments behind a trusted reverse proxy may require throttling by the real client address conveyed by a trusted proxy header such as X-Real-IP or Forwarded. This is not enabled by this WorkLog because such headers must only be trusted when the proxy is explicitly trusted/configured; otherwise directly connected clients could spoof them to bypass perHost.* throttling. A future design may add trusted-proxy configuration and separate real-client-IP throttling controls.

Throttling Rules and Behaviour

  1. Tracking of Authentication Attempts

Each authentication attempt is tracked per host. MySQL Internal and MRS vendor attempts are additionally tracked per presented account identifier.

Rate Limit Per Minute

If the number of authentication attempts within the last minute exceeds:

  • perAccount.maximumAttemptsPerMinute, or
  • perHost.maximumAttemptsPerMinute

Then the request is rejected with: HTTP 429 Too Many Requests

Minimum Time Between Requests

If an authentication request arrives sooner than:

  • perAccount.minimumTimeBetweenRequestsInMs, or
  • perHost.minimumTimeBetweenRequestsInMs

Then the request fails with: HTTP 429 Too Many Requests

Blockout Period

When throttling is triggered:

  • The applicable per-account or per-host key enters a blocked state
  • All subsequent authentication attempts for blockWhenAttemptsExceededInSeconds are automatically rejected with 429 Too Many Requests

Successful and unsuccessful authentication attempts are counted against their applicable limits. This protects against brute-force password guessing and abusive authentication retry/session-creation loops, including excessive load on authentication backends. Per-account limits apply to credential attempts, while per-host limits apply to requests entering the full authentication path. Ordinary data requests that only check an existing session and raw HTTP connection establishment are not throttled. Authentication-required content-file requests enter the full authentication path and remain subject to per-host limits even when using an existing session.

  1. Request Payload Size Limiting

In this initial WorkLog, request-body handling follows the behavior of the embedded HTTP server layer.

This WorkLog does not define a new administrator-visible limit for maximum HTTP request body size, and it does not define a specific threshold for an "oversized" payload.

As a result:

  • this WorkLog does not guarantee a specific rejection threshold for large request bodies;
  • this WorkLog does not define protection against aggregate resource exhaustion caused by many concurrent smaller requests;
  • request handling for large bodies remains whatever is provided by the embedded HTTP server implementation.

Explicit global controls for maximum concurrent HTTP connections, maximum HTTP request body size, and maximum HTTP response body size are introduced separately.

  1. Protection Scope

The MRS DoS protection mechanisms in this WorkLog defend against:

  • password brute-forcing
  • authentication flooding on a per-host basis for all vendors and on a per-account basis for MySQL Internal and MRS vendor flows
  • continuous abusive authentication retries

This WorkLog does not:

  • define a global limit for concurrent HTTP client connections;
  • define a global limit for HTTP request body size;
  • define a global limit for HTTP response body size;
  • guarantee protection against aggregate resource exhaustion caused by many simultaneous connections or requests;
  • protect against overwhelming volumes of TCP connection attempts;
  • replace MySQL firewall or network-layer filtering;
  • provide query-level resource governors for CPU, memory, or execution time.

These aspects remain the responsibility of:

  • the HTTP server layer and its follow-up configuration controls;
  • network-layer controls such as firewalls and proxies;
  • MySQL Server process-level and operating-system resource limits.

Explicit HTTP connection, request-body, and response-body limits are introduced separately.

  1. Security Characteristics

    • DoS throttling logic executes before SQL execution
    • No information leakage occurs (429 does not reveal whether credentials were valid)
    • Per-account and per-host block states are isolated by their respective keys
    • Per-host throttling applies to all REST authentication vendors; per-account throttling applies to MySQL Internal and MRS vendor flows

Protocol Details

(Supports FR3, FR5)

The embedded MRS component exposes the existing MySQL Router-hosted MRS RESTful HTTP protocol surface, subject to the explicit component-mode limitation below.

Component-hosted MRS does not support executing REST procedures or functions configured with mysqlTask.driver = "router". An invocation of such an endpoint returns HTTP 501 (Not Implemented). The component does not map this setting to mysqlTask.driver = "database" because the drivers have different execution semantics. Supporting the Router driver in component mode requires a component-compatible asynchronous execution subsystem and is outside WL#17018.

This WorkLog does not introduce a new wire protocol, new message format, or new client interaction model. Instead, it reuses the existing MRS HTTP API and embeds its implementation directly into mysqld.

In particular:

  • transport is HTTP/1.1 over TLS
  • request and response payloads use the existing MRS formats, primarily JSON; static-content and media endpoints may return non-JSON or binary response bodies
  • the REST request model and supported HTTP methods remain those of the existing MRS implementation
  • authentication flows remain those defined for the existing MRS implementation
  • except for the unsupported Router-specific MySQL task driver described above, this WorkLog changes the hosting and server integration model, not the externally visible REST protocol semantics

Transport Protocol

  • Protocol: HTTP/1.1
  • Port: 33443 (default; configurable in future WLs)
  • TLS: Mandatory; the REST endpoint is available only when MySQL Server is configured with valid SSL certificate and key material

No custom binary protocol, no RPC mechanism, and no MySQL native protocol are exposed.

Request model

REST clients interact using standard HTTP semantics:

  • GET: Retrieve rows or collection metadata
  • POST: Insert or update data; perform actions
  • PUT: Update or insert a resource using its full representation
  • DELETE: Remove resources

The URI structure, resource semantics, and JSON request/response shapes are unchanged from the existing MRS protocol and are not redefined by this WorkLog.

Authentication and Authorization

Request authentication and SQL execution identity depend on the service configuration and, for authenticated access, the "REST AUTH VENDOR":

  1. MySQL Internal vendor 1.1. client presents MySQL username/password using HTTP Basic authentication over TLS 1.2. MRS performs authentication using the MySQL authentication framework 1.3. password material is used only during authentication, is handled using the existing Router/MRS protected in-memory mysql_harness::SecureString, and is not stored in MRS metadata, logs, JWTs, cookies, reusable HTTP session state, or a component password cache 1.4. after authentication, repeated access is based on MRS session state and the authenticated MySQL identity and security context 1.5. MRS authorizes the requested REST resource and operation using the REST configuration and MRS metadata 1.6. for services configured with passthroughDbUser = true, only users authenticated through the MySQL Internal vendor are allowed, and SQL executes under the authenticated user's security context with that user's MySQL grants 1.7. for services configured with passthroughDbUser = false, SQL executes through mysql_mrs_data using mysql_rest_service_data_provider

  2. MRS vendor 2.1. client presents credentials for an MRS REST Service specific account 2.2. MRS authenticates the user using the SCRAM-SHA-256 flow 2.3. authentication data is verified against the SCRAM material stored in mysql_rest_service_metadata.mrs_user.auth_string 2.4. on success, the component issues either a session cookie or a JWT, depending on the selected session type 2.5. subsequent requests validate the session cookie or the JWT signature and token lifetime 2.6. for JWT sessions, the component generates a cryptographically strong random signing key at startup and uses it to sign and validate component-issued JWTs 2.7. the signing key is held only in memory and is not persisted or user-configurable in this WorkLog; restarting the component or server invalidates JWTs signed with the previous key 2.8. MRS authorizes the user using the assigned MRS roles and REST privileges, which may be scoped to a service, schema, object, and CRUD operation 2.9. after MRS authorization succeeds, SQL executes through mysql_mrs_data using mysql_rest_service_data_provider

  3. OAuth2 vendor 3.1. client presents a bearer token 3.2. token is validated according to vendor configuration 3.3. the authenticated OAuth2 identity is resolved to an MRS user 3.4. MRS authorizes that user using the assigned MRS roles and REST privileges, which may be scoped to a service, schema, object, and CRUD operation 3.5. after MRS authorization succeeds, SQL executes through mysql_mrs_data using mysql_rest_service_data_provider

  4. Unauthenticated access 4.1. the client does not present authentication credentials 4.2. MRS permits access only to services and resources explicitly configured to allow unauthenticated access 4.3. SQL executes through mysql_mrs_data using mysql_rest_service_data_provider

No authentication secrets are exchanged in cleartext. The internal MySQL users (mysql_mrs_metadata and mysql_mrs_data) are never exposed to external clients.

Server-Side Execution (How HTTP Mapped to MySQL)

After validating the request:

  1. The REST backend uses the existing MRS request-processing and data-mapping implementation to construct one or more SQL statements corresponding to the REST action

    Depending on the target REST object and operation, generated statements may include SELECT, INSERT, UPDATE, DELETE, or CALL. A REST mutation does not necessarily map one-to-one to a single SQL statement or SQL verb.

    For a REST data mapping view that spans related tables, a mutation may require multiple ordered DML statements. The existing MRS data-mapping logic derives these statements from the mapping relationships and enabled CRUD operations and executes the mutation within a transaction.

    This mapping-level behavior is independent of the foreign-key referential actions declared in the database schema. This WorkLog introduces no component-specific emulation or override of ON UPDATE or ON DELETE actions. MySQL enforces the declared foreign-key constraints and referential actions for each generated statement. If any statement fails, the REST request fails and the mutation transaction is rolled back.

  2. The component attaches the application-data execution security context selected for the request—the authenticated MySQL user's context for MySQL-passthrough requests, or mysql_mrs_data for non-passthrough requests—to a THD and executes the generated SQL statements through the server execution path

  3. Each SQL statement is executed using an internal execution path chosen by the MRS runtime:

    • Prepared statements may be used where they fit the generated statement shape efficiently.
    • Direct SQL execution may be used for internally generated statements whose final SQL text varies per request.
  4. Results are serialized according to the existing MRS endpoint semantics: normally as JSON, or using the detected media type for media responses. Errors use the existing MRS error format.

The component does not execute raw client-supplied SQL. SQL is generated internally from MRS metadata and validated request context. This WorkLog does not require all internally generated statements to be executed as prepared statements.

The Router-hosted connection-cache structure described in the Connection Management section is not used for normal component-hosted MRS request handling in this WorkLog.

Protocol Security Characteristics

  • Fully based on HTTP using the existing MRS JSON and media payload formats; no new custom protocol
  • Encrypted over TLS; the REST endpoint is available only when MySQL Server is configured with valid TLS material
  • Uses industry-standard authentication mechanisms
  • For the built-in MRS authentication vendor, JWT validation is local to the running component instance.
  • Internal MySQL protocol is never exposed to clients
  • No server-to-client push, no streaming beyond HTTP semantics
  • Supports binary response bodies through existing MRS static-content and media endpoint semantics; this WorkLog introduces no new binary payload format
  • No multiplexing

Resource Control

(supports NFR2, NFR4)

The MRS Component executes within the MySQL Server process and relies on embedded MySQL Router subsystems (IO, HTTP, MRS, etc.). Resource usage is therefore determined by a combination of current embedded subsystem behavior, explicit component-level limits defined by this WorkLog, MySQL Server process-level limits, operating-system resource limits, and future MRS-specific configuration interfaces introduced in follow-up WorkLogs.

In this WorkLog, the resource restrictions explicitly defined by the design are limited to:

  • the bounded number of IO worker threads created by the embedded Router IO subsystem
  • the per-authenticated-MRS-session limit on concurrently active embedded SQL sessions for MySQL-passthrough execution, defined by passthroughDbUser.poolSize
  • the shared MySQL Server process-level and operating-system resource limits that apply because the component runs inside mysqld

The component reads selected MySQL system variables during startup to discover required server configuration (for example, port and SSL-related settings). In this WorkLog, those system variables are used for initialization and compatibility checks, not as a new MRS-specific resource-governance interface.

This WorkLog does not define an explicit limit for SQL result size or serialized HTTP response size. A separate WorkLog introduces an HTTP-layer max_response_body_size guard before a response is sent. This guard does not bound the SQL result itself or memory consumed while materializing and serializing the response. An MRS-level result limit, for example max_rows_per_response, remains future work.

Thread Usage

Thread creation for serving inbound REST traffic is performed by the embedded Router IO/HTTP runtime, not by MRS-specific application logic.

Thread Count

The embedded Router IO subsystem creates IO worker threads used by the HTTP runtime to serve inbound REST traffic.

By default, component-hosted MRS uses 25% of the available logical CPUs, rounded up, with a minimum of one IO worker thread. A follow-up WorkLog introduces an administrator-visible control for this limit.

This component-specific policy does not change standalone MySQL Router behavior and will be revisited using mixed MRS and SQL workload measurements.

These are runtime IO/HTTP threads used to serve REST traffic. The MRS plugin itself does not introduce an additional per-request or per-CPU MRS-specific thread pool, and no additional unbounded thread creation occurs.

Thread Lifecycle

  • Threads are created once during the MRS component asynchronous startup path, when the embedded Router IO/HTTP runtime is initialized
  • Threads remain active until component shutdown
  • No per-request thread creation (avoids thread explosion)
  • No thread pools are dynamically resized

Safety Characteristics

  • Thread count is bounded and predictable
  • Controlled entirely by CPU count (unless explicitly overridden in a future WL)
  • Safe for multi-tenant or containerized deployments

Interaction with MySQL Server Limits

Because the component runs in-process, it shares the mysqld process budget for CPU time, memory, file descriptors, and scheduling. Resource pressure caused by the component therefore contributes to the same process-level limits that govern the server as a whole.

For WL17018, the interaction with MySQL Server limits is intentionally narrow:

  • this WorkLog does not define a separate quota layer derived from existing MySQL system variables
  • this WorkLog does not define max_connections as a limit for inbound HTTP clients accepted by the embedded HTTP server
  • SQL executed through MySQL component services continues to run under the server's normal execution infrastructure, but this WorkLog does not introduce new MRS-specific governors on top of that path

Administrator-visible MRS-specific resource-governance controls are introduced in follow-up WorkLogs, including HTTP-layer connection and request-body limits and SQL-facing MRS configuration interfaces.

File Descriptors and Runtime Limits

The component does not create or manage application-data or temporary files. The embedded HTTP server reads the configured TLS certificate and private-key files during initialization. Standard logging is handled by MySQL Server.

Internal MySQL Sessions

Component-hosted metadata and application-data SQL execution uses the MySQL command-service path with internal Srv_session-backed THDs and THD-attached security contexts, not outbound network connections. MRS/Router HTTP worker threads are not bound to a THD for their entire lifetime; a THD is required only for the SQL execution portion of request handling. The command-service session holds the server session/THD while connected and releases it when the command-service session is closed.

For Router-hosted execution paths that retain reusable internal MySQL session objects, retention is managed by the MRS backend through the cache structure.

The retained-session cache is managed by:

  • /mysql/cache/metadata/ro_instances
  • /mysql/cache/metadata/rw_instances
  • /mysql/cache/userdata/ro_instances
  • /mysql/cache/userdata/rw_instances

Therefore, for Router-hosted execution paths:

  • internal session retention is managed by the cache
  • idle session retention is controlled by cache configuration
  • sessions are only retained while cached; excess sessions are discarded

For component-hosted metadata and application-data SQL execution, embedded sessions are created on demand and closed when returned. They are not retained idle for reuse across requests, and the mysql.cache.* configuration does not change this lifecycle.

MySQL-passthrough execution is bounded by passthroughDbUser.poolSize as described in Connection Management & Lifecycle.

Inbound Connections (HTTP Clients)

In this initial WorkLog, inbound REST connections follow the current behavior of the embedded HTTP server implementation and remain governed primarily by OS and process-level limits.

This WorkLog does not introduce an administrator-visible limit for concurrent HTTP client connections, and it does not define a bound on aggregate resource use caused by many simultaneous client connections.

Explicit max_http_connections, max_request_body_size, and max_response_body_size controls are introduced separately and are intended to be used by embedding implementations such as the MRS component.

Real Files

The MRS component:

  • Reads the configured TLS certificate and private-key files for HTTP TLS initialization
  • Does not create or manage application-data files
  • Relies solely on existing MySQL Server log infrastructure
  • Uses no temporary file storage
  • Does not depend on Router's file-based keyring

Memory Usage

Memory Allocation Model

MRS uses memory for:

  • HTTP request parsing
  • JSON serialization/deserialization
  • SQL result conversion
  • Connection cache internal metadata

In this WorkLog, memory usage is influenced by the behavior of the embedded HTTP server and Router runtime, MySQL Server process limits, and operating-system resource limits.

This WorkLog does not define a component-specific memory quota or explicit Performance Schema memory instrumentation for these allocations. Because the embedded Router/MRS runtime does not use a THD-owned allocation context for these internal buffers, THD::mem_root is not the allocation model for this part of the design. Explicit memory instrumentation, using component-specific PSI memory keys, is outside the scope of this WorkLog.

Cross-Request Runtime State

  • The embedded MRS runtime retains in-process authentication/session state and response or content-file cache entries across requests.
  • This retained state follows the existing MRS timeout, eviction, and cache-limit behavior. WL#17018 introduces no component-specific aggregate memory limit.

No Direct Memory Limit Enforcement

MRS does not impose its own memory quota system in this WorkLog.

WL#17018 introduces no component-specific aggregate memory quota. A separate WorkLog adds HTTP-layer limits for concurrent connections and request and response bodies, but its response-body guard does not bound memory consumed while constructing a response.

Logging Integration

(Implements FR5, NFR3, NFR4)

The component introduces a logging sink that maps Router log levels to MySQL Server log levels:

Log level mapping:

+------------------------------------------------------------------+
| Router LogLevel  |   Component Level    | (log_error_verbosity)  |
+------------------+----------------------+------------------------+
| SYSTEM           | SYSTEM_LEVEL (0)     | Always                 |
| FATAL            | ERROR_LEVEL (1)      | 1, 2, 3                |
| ERROR            | ERROR_LEVEL (1)      | 1, 2, 3                |
| WARNING          | WARNING_LEVEL (2)    | 2, 3                   |
| INFO             | INFORMATION_LEVEL(3) | 3                      |
| NOTE             | INFORMATION_LEVEL(3) | 3                      |
| DEBUG            | INFORMATION_LEVEL(3) | 3                      |
| default (INFO)   | INFORMATION_LEVEL(3) | 3                      |
+------------------+----------------------+------------------------+

At component startup, the embedded logging threshold is initialized from log_error_verbosity. The default value of 2 hides INFO/NOTE/DEBUG; set it to 3 before component startup to include those messages. log_filter_dragnet can further filter messages forwarded to the server log.

If the embedded stack cannot be initialized, a clear error message is emitted through this logging channel.

Compatibility and Coexistence

The component is statically linked with required Router libraries (IO, HTTP, Harness, MRS) to ensure version consistency and avoid runtime plugin dependencies. WL#17018 does not introduce any new third-party library dependency; it reuses existing in-tree Router/MRS code and dependencies already present in the MySQL Server/Router build.

Coexistence with Router-hosted MRS

WL#17018 does not stop or reconfigure an external MySQL Router process. It also does not define Router-hosted MRS and component-hosted MRS as a coordinated active-active deployment.

If both runtimes target the same MySQL deployment during an operator-controlled transition:

  • Both read the persistent REST definitions stored in mysql_rest_service_metadata and access the same application data. Metadata changes can therefore become visible to both through their normal metadata-refresh paths.
  • Writes received through both endpoints execute independently against the same application data; WL#17018 provides no cross-runtime serialization. Existing MRS and MySQL concurrency semantics apply: MRS data-mapping mutations execute in transactions, updates lock the affected rows and validate an ETag when supplied, and MySQL enforces transaction isolation and database constraints. Conflicting writes may fail, and without an ETag a later successful update may replace earlier values according to normal SQL semantics. Clients must handle such failures and retry only when safe. The controlled migration procedure below avoids normal write overlap by stopping new Router-hosted requests before cutover.
  • The component creates or updates its own MRS runtime registration. Its HTTP listener endpoint and (address, router_name) registration identity must not conflict with an existing Router instance; a conflict causes startup to fail.
  • HTTP connections, session-cookie state, caches, and in-flight requests are runtime-local and are not transferred between the Router and the component.
  • The component uses its own restart-scoped JWT signing key and does not import the JWT signing material stored by Router.
  • Clients using MRS session cookies or JWTs issued by Router-hosted MRS must authenticate again when moved to the component endpoint.
  • Requests sent to both endpoints are processed independently and consume database resources independently. WL#17018 provides no cross-runtime traffic coordination, load balancing, failover, session sharing, or request handoff.
  • Component-hosted MRS moves the HTTP listener, TLS termination, MRS worker threads, and associated resource usage into mysqld; its lifecycle and availability are tied to that MySQL Server instance.

MySQL Router can remain required for classic-protocol routing, topology discovery, load balancing, or failover. Replacing Router-hosted MRS does not imply removing the Router process when it provides those functions.

WL#17018 does not guarantee long-running coexistence, coordinated active-active operation, or session continuity between the two runtimes.

Migration from Router-hosted MRS

WL#17018 does not provide an automatic migration or cutover operation. The migration described here applies when the component is installed on the same standalone MySQL Server that stores the MRS metadata and application data used by Router-hosted MRS.

The component reuses the existing mysql_rest_service_metadata schema, REST definitions, application data, and provider-role grants; no metadata or application-data export and import is required. The component creates its own runtime registration and internal execution identities. It does not import Router configuration, keyring entries, account credentials, JWT signing material, HTTP sessions, or in-flight requests.

A controlled migration consists of:

  1. Verify that the existing MRS metadata version is supported, required services are enabled and published, required provider-role grants are present, and the component listener and registration identity will not conflict with an existing Router instance.
  2. During a planned service interruption, stop directing new requests to Router-hosted MRS, handle any in-flight Router requests according to the existing Router shutdown procedure, and stop the Router-hosted MRS endpoint. Requests and sessions are not transferred to the component.
  3. Install the component, wait for it to become operational, and validate the published REST services through the component endpoint.
  4. Update the REST base URL, proxy or DNS routing, and client TLS trust as required. Clients using Router-issued MRS session cookies or JWTs must authenticate again.
  5. Retain the Router process if it continues to provide classic-protocol routing or topology-related functions. Shared MRS metadata and provider-role grants must not be removed as part of the cutover.

Cleanup of Router-specific configuration, keyring material, and MySQL accounts is outside WL#17018 and must not be performed automatically.

Rollback consists of stopping component-hosted MRS, re-enabling the previously configured Router-hosted MRS endpoint, and directing REST traffic back to it. REST service definitions and application data do not require reverse migration. Any Router registration changed to resolve an identity conflict must be restored, and affected clients must authenticate again.

Migration between different MySQL deployments, movement of metadata or application data, preservation of sessions or in-flight requests, guaranteed zero-downtime cutover, coordinated active-active operation, and topology-equivalent replacement of Router deployments using InnoDB Cluster, InnoDB ReplicaSet, or InnoDB ClusterSet capabilities are outside the scope of WL#17018.

Interfaces Used / Required

(Supports NFR1, NFR3)

MySQL Server Component Services

  • Logging: log_builtins, log_builtins_string
  • Server Configuration Reads: mysql_system_variable_reader
  • TLS Configuration Inspection: table_access_factory_v1, table_access_v1, table_access_scan_v1, field_varchar_access_v1, mysql_string_factory, mysql_string_get_data_in_charset, mysql_string_converter
  • SQL Command Execution: mysql_command_* (factory, query, error_info)
  • Prepared Statements: mysql_stmt_* (execute_direct, metadata, bind)
  • Thread/Security Context: mysql_current_thread_reader, mysql_thd_security_context, mysql_security_context_factory, mysql_account_database_security_context_lookup, mysql_security_context_options

System-variable and status-variable registration, UDF registration, and their associated testing interfaces are owned by WL#17019 and are not required by WL#17018.

Embedded MySQL Router Libraries

  • io
  • http_server
  • routing
  • mysql_rest_service

All are statically linked into the component and executed in-process as built-in Router Harness plugins; no Router plugin shared libraries are loaded at runtime.

Error Handling and Logging Behaviour

(Implements NFR4)

  • Failures during initialization (e.g., TLS disabled, invalid SSL configuration, security context creation errors, or metadata schema errors) produce clear, actionable log entries.
  • Runtime errors in the background thread are logged asynchronously.
  • Logging uses the standard Component Logging API and adheres to log_error_verbosity.

Future Extensions

(Implements FR7)

The component includes internal hooks for adding: - System variables and status variables to configure and monitor operation. - Lifecycle-control UDFs defined by WL#17019.

Resource-governance controls for the embedded HTTP-facing runtime are introduced in follow-up worklogs, including SQL-facing MRS configuration variables and HTTP server support for explicit connection and request-size limits.

Internal architecture

MRSComponent
  ├─ ServerConfig
  ├─ Log
  ├─ SecurityContextHandler
  └─ Backend
       └─ RouterConfig
           └─ MRSAccount

MRSComponent

The central orchestrator of the component:

  • Manages the lifecycle of all other component parts
  • Coordinates configuration, logging, and backend initialization.
  • Acts as the main entry point for setup and teardown.

Backend

Implements the runtime backend of the component:

  • Handles core service logic such as metadata access, plugin loading, and threading.
  • Integrates with the Router and security context subsystems.
  • Uses RouterConfig to configure the internal service.
  • Manages lifecycle transitions (init, run, stop).

RouterConfig

Runtime configuration holder for the embedded Router:

  • Contains HTTP port, SSL certs, identity, and routing-related metadata.
  • Used by Backend to initialize and launch the embedded Router stack.

MRSAccount

Identity container for the embedded MRS Router instance:

  • Stores the MySQL account names used for internal metadata and data execution.
  • Used by RouterConfig for account provisioning and access control.

ServerConfig

Handles MySQL server configuration:

  • Retrieves runtime system variables (basedir, datadir, port, etc.).
  • Supplies values needed to configure the backend and Router.

Log

Component-integrated logging facility:

  • Wraps the MySQL server logging framework.
  • Supports formatted messages, severity levels, and component tagging.

SecurityContextHandler

Helper class to encapsulate interactions with the MySQL security context service. Provides a minimal API to:

  • Create security contexts for the internal MRS metadata and data accounts
  • Attach the security context to a THD for internal SQL execution
  • Restore or release the security context after execution
  • Validate that the internal accounts and required roles are available

Authorization Model / Role Realization

The authoritative SQL definitions for MRS roles and grants are maintained in the mysql_rest_service_metadata schema creation script, in the Authorization section.

The metadata schema defines the standard MRS roles, including:

CREATE ROLE IF NOT EXISTS
  'mysql_rest_service_admin',
  'mysql_rest_service_schema_admin',
  'mysql_rest_service_dev',
  'mysql_rest_service_user',
  'mysql_rest_service_meta_provider',
  'mysql_rest_service_data_provider';

The embedded MRS runtime depends specifically on the following provider roles:

  • mysql_rest_service_meta_provider

    • Used by the embedded MRS runtime to read MRS metadata required to identify and serve REST services.
  • mysql_rest_service_data_provider

    • Used by the embedded MRS runtime to access application data exposed through REST services.
    • Must hold the privileges required on the underlying database schema objects referenced by REST endpoints.
    • For REST views exposing tables or views, required privileges are granted automatically.
    • For REST procedures and REST functions, the EXECUTE privilege on the exposed routine is granted automatically.
    • If an exposed routine accesses additional procedures or other schema objects, additional manual GRANT statements may still be required.

The exact GRANT matrix is intentionally not duplicated in this WorkLog to avoid divergence from the schema definition.

Component Lifecycle

Startup

static mysql_service_status_t mysql_rest_service_init()

1) Allocates and initializes the main handler class

extern std::unique_ptr<MRSComponent> s_mrs_component;  // main handler

// main handler accessor
MRSComponent &mrs_component();

class MRSComponent {
 public:
  // c-tors
  ...

  // Services init/register methods
  int server_config_init();
  int system_vars_init();
  int system_vars_register();
  ...

  // Backend class init/stop
  int backend_init();
  int backend_stop();

  mysql_service_status_t component_init();
  mysql_service_status_t component_deinit();

  // Getters
  ServerConfig &server_config() { return m_server_config; }
  SystemVars &system_vars() { return m_system_vars; }
  ...

 private:
  // Class members
  ...

  ServerConfig m_server_config;
  ...
  Log m_log;
  Backend m_backend;
};

2) Allocates and initializes the "services" and the Backend object responsible for managing the embedded MRS stack

(...)
std::string_view log_str = "Initializing Server Configuration handler";
MRS_LOG_INFO("%s", log_str.data());

if (server_config_init() != 0) return error(log_str);
(...)

set_initialized(true);

log_str = "Initializing Backend";
MRS_LOG_INFO("%s", log_str.data());

if (backend_init() != 0) return error(log_str);
(...)

2.1) Reads relevant system variables (e.g., user, port, SSL paths)

int MRSComponent::server_config_init() {
  MRS_LOG_INFO("Fetching required system variables from the Server");
  return server_config().fetch_required_sysvars();
}

3) Registers the Router plugin entry points statically linked into the component as built-in plugins with the embedded Harness loader

void Backend::init_builtins() {
  const char *k_mrs_plugin_name = "mysql_rest_service";
  auto &builtins = mysql_harness::BuiltinPlugins::instance();

  if (builtins.has(k_mrs_plugin_name)) {
    // Builtins already registered.
    return;
  }

  builtins.add(k_mrs_plugin_name, {&harness_plugin_mysql_rest_service, false});
  builtins.add("io", {&harness_plugin_io, false});
  builtins.add("http_server", {&harness_plugin_http_server, false});
  builtins.add("host_cache", {&harness_plugin_host_cache, false});
  builtins.add("routing", {&harness_plugin_routing, false});

  builtins.add("router_protobuf", {&harness_plugin_router_protobuf, false});
  builtins.add("router_openssl", {&harness_plugin_router_openssl, false});
  builtins.add("connection_pool", {&harness_plugin_connection_pool, false});
  builtins.add("destination_status",
               {&harness_plugin_destination_status, false});
#ifdef COMPONENT_MRS_USE_JIT_EXECUTOR
  builtins.add("jit_executor", {&harness_plugin_jit_executor, false});
#endif
}

4) Initializes the logging sink

void ComponentlogHandler::init_log_service(SERVICE_TYPE(log_builtins) *
                                           log_builtins_ptr,
                                       SERVICE_TYPE(log_builtins_string) *
                                           log_builtins_string_ptr) {
  if (s_inited) return;

  log_bi = log_builtins_ptr;
  log_bs = log_builtins_string_ptr;

  s_inited = true;
}

5) Sets member variables with configurations

6) Starts the main service thread (backend)

// Start the service thread using the stored configuration
 m_service_thread = std::thread([this, p = std::move(init_result)]() mutable {
    try {
      // run() does the initialization of the backend, spawns another thread
      // enters a long-running loop and returns. Pass along the promise.
      run(std::move(p));
    } catch (const std::exception &e) {
      // If run() fails during initialization log the error
      MRS_LOG_ERROR("Backend startup failed: %s", e.what());
    }
  });

  // Wait for run() to complete minimal init (right before spawning the md
  // schema checker)
  return init_future.get();

6.1) Initializes internal Router subsystems (DIM, etc.) 6.2) Setups the logger 6.3) Signals successful minimal startup so the service thread can return early

7) Spawns another thread (backend_started_thread)

7.1) It waits on a loop until the Metadata Schema is found

8) Configures the internal MRS accounts

9) Populates the MRS metadata schema (router table) - auto-bootstrap

10) Configures the loader

11) Initializes the security context handler for the internal MRS accounts

12) Starts the loader

Shutdown / Failure

static mysql_service_status_t mysql_rest_service_deinit()

1) Stops the backend

1.1) Stops accepting new HTTP work and signals the embedded harness/runtime to stop

1.2) Cancels or joins any pending asynchronous startup path

1.3) Waits for the backend and backend-startup threads to exit

1.4) Closes or releases active command-service/Srv_session state through normal server session/THD cleanup; worker threads must not be forcibly terminated while SQL execution is active

1.5) Clears and releases internal security context state

1.6) Resets the Loader

2) Cleans up configuration and thread context.

MySQL Router Static Libraries

To embed the MySQL REST Service stack directly within the MySQL Server process, the component statically links selected MySQL Router internal object libraries.

The primary Router targets required are:

  • http_server_object — provides the HTTP server framework used to expose REST endpoints.

  • metadata_cache_object — enables access to topology and metadata information.

  • mysql_rest_service_object — contains the MySQL REST Service Harness plugin entry point and statically linked plugin implementation.

These object libraries depend on additional Router modules (e.g., networking, routing, connection pooling, SSL/TLS, etc.). Such dependencies are resolved automatically through CMake and are not listed explicitly here, as they may evolve with future Router refactoring.

All required object libraries are statically linked at build time to produce a self-contained component that embeds the REST Service within the MySQL Server.

Additionally, shared C++ utilities code from the Router source tree are included.