refactor: reorganise optional SQL scripts by database type
The optional SQL directory contained a single PostgreSQL script with no clear organisation. As we now have scripts for both PostgreSQL and MSSQL, and multiple test scenarios (message generation, room creation, performance testing), a clearer structure is needed. Reorganises into postgresql/ and mssql/ subdirectories with descriptive filenames that indicate purpose rather than execution order. Adds README documenting available scripts and usage patterns. Key scripts preserved: - 410k message generator (PostgreSQL + MSSQL) - 50 room creator with message redistribution (PostgreSQL + MSSQL) - 10,000 minimal rooms for scale testing (PostgreSQL) - 200 rooms with realistic affiliations and messages (PostgreSQL) - Worker count configuration template (PostgreSQL)feat/add-optional-sql-scripts
parent
f96acacafb
commit
582c7269c9
|
|
@ -0,0 +1,82 @@
|
|||
# Optional SQL Scripts
|
||||
|
||||
This directory contains optional SQL scripts for generating test data in Openfire Docker environments. These scripts are useful for performance testing, debugging, and simulating production-like environments.
|
||||
|
||||
## Directory Structure
|
||||
|
||||
```
|
||||
optional/sql/
|
||||
├── postgresql/ # Scripts for PostgreSQL databases
|
||||
│ ├── generate-test-messages.sql
|
||||
│ ├── create-50-rooms.sql
|
||||
│ ├── performance-test-10000-rooms.sql
|
||||
│ ├── performance-test-200-rooms-with-data.sql
|
||||
│ └── set-worker-count.sql
|
||||
└── mssql/ # Scripts for Microsoft SQL Server
|
||||
├── generate-test-messages.sql
|
||||
└── create-50-rooms.sql
|
||||
```
|
||||
|
||||
## Available Scripts
|
||||
|
||||
### PostgreSQL Scripts
|
||||
|
||||
| Script | Purpose |
|
||||
|--------|---------|
|
||||
| `generate-test-messages.sql` | Generates ~410,000 MUC messages across 2 rooms. Useful for testing slow startup issues due to large message history. |
|
||||
| `create-50-rooms.sql` | Creates 48 additional rooms (IDs 3-50) and redistributes messages across all 50 rooms. |
|
||||
| `performance-test-10000-rooms.sql` | Creates 10,000 minimal rooms with single owner affiliation. Ideal for testing room loading at scale without message history overhead. |
|
||||
| `performance-test-200-rooms-with-data.sql` | Creates 200 rooms with realistic data: varied affiliations (owners, admins, members) and 100-500 messages per room (~60,000 total). |
|
||||
| `set-worker-count.sql` | Template for setting the `xmpp.muc.loading.workers` property to control parallel room loading. |
|
||||
|
||||
### MSSQL Scripts
|
||||
|
||||
| Script | Purpose |
|
||||
|--------|---------|
|
||||
| `generate-test-messages.sql` | MSSQL version of the 410,000 message generator. |
|
||||
| `create-50-rooms.sql` | MSSQL version of the 50 rooms creator. |
|
||||
|
||||
## Usage
|
||||
|
||||
### Option 1: Copy to deployment directory (recommended for testing)
|
||||
|
||||
Copy the desired script to your deployment's `sql/` directory with a numbered prefix:
|
||||
|
||||
```bash
|
||||
# For simple deployment with 10,000 rooms
|
||||
cp optional/sql/postgresql/performance-test-10000-rooms.sql simple/sql/001-perf-rooms.sql
|
||||
|
||||
# Start fresh (removes existing database)
|
||||
./start.sh
|
||||
```
|
||||
|
||||
Scripts in the `sql/` directory run automatically on container startup via PostgreSQL's `docker-entrypoint-initdb.d` mechanism.
|
||||
|
||||
### Option 2: Run manually against running database
|
||||
|
||||
```bash
|
||||
# PostgreSQL example
|
||||
docker exec -i simple-db-1 psql -U openfire -d openfire \
|
||||
< optional/sql/postgresql/generate-test-messages.sql
|
||||
|
||||
# MSSQL example
|
||||
docker exec -it mssql_server /opt/mssql-tools18/bin/sqlcmd \
|
||||
-S localhost -U sa -P 'YourPassword' -d openfire -C \
|
||||
-i /path/to/script.sql
|
||||
```
|
||||
|
||||
## Choosing a Test Dataset
|
||||
|
||||
| Use Case | Recommended Script |
|
||||
|----------|-------------------|
|
||||
| Test MUC history loading performance | `generate-test-messages.sql` + `create-50-rooms.sql` |
|
||||
| Test room loading at scale (many rooms, no messages) | `performance-test-10000-rooms.sql` |
|
||||
| Test realistic room loading (rooms with affiliations + messages) | `performance-test-200-rooms-with-data.sql` |
|
||||
| Test parallel worker configuration | Any data script + `set-worker-count.sql` |
|
||||
|
||||
## Notes
|
||||
|
||||
- Scripts numbered `001-*` onwards run after `000-init-openfire.sql` (the base schema)
|
||||
- Some scripts (like `create-50-rooms.sql`) expect existing rooms/messages to work with
|
||||
- Performance test scripts replace existing rooms, so use on fresh databases
|
||||
- Worker count changes require an Openfire restart to take effect
|
||||
|
|
@ -0,0 +1,122 @@
|
|||
-- =============================================================================
|
||||
-- Create 50 MUC Rooms - MSSQL
|
||||
-- =============================================================================
|
||||
--
|
||||
-- Database: Microsoft SQL Server
|
||||
-- Compatibility: MSSQL deployments (cluster_mssql)
|
||||
--
|
||||
-- Purpose:
|
||||
-- Creates 48 additional MUC rooms (IDs 3-50) to supplement the 2 default rooms,
|
||||
-- giving a total of ~50 rooms. Also redistributes any existing messages evenly
|
||||
-- across all 50 rooms.
|
||||
--
|
||||
-- Useful for testing environments that need a moderate number of rooms with
|
||||
-- message history spread across them.
|
||||
--
|
||||
-- Prerequisites:
|
||||
-- - Rooms with IDs 1 and 2 should already exist
|
||||
-- - Best used after generate-test-messages.sql to have messages to redistribute
|
||||
--
|
||||
-- Usage:
|
||||
-- Run manually against a running MSSQL database:
|
||||
--
|
||||
-- docker exec -it mssql_server /opt/mssql-tools18/bin/sqlcmd \
|
||||
-- -S localhost -U sa -P 'YourPassword' -d openfire -C \
|
||||
-- -i /path/to/create-50-rooms.sql
|
||||
--
|
||||
-- =============================================================================
|
||||
|
||||
USE openfire;
|
||||
GO
|
||||
|
||||
SET NOCOUNT ON;
|
||||
GO
|
||||
|
||||
DECLARE @i INT = 3;
|
||||
DECLARE @room_name VARCHAR(50);
|
||||
DECLARE @creation_time CHAR(15);
|
||||
DECLARE @base_time BIGINT = CAST(DATEDIFF(SECOND, '1970-01-01', GETDATE()) AS BIGINT) * 1000;
|
||||
|
||||
PRINT 'Creating additional MUC rooms...';
|
||||
PRINT 'Current time (ms): ' + CAST(@base_time AS VARCHAR(20));
|
||||
|
||||
-- Create rooms 3 through 50 (48 additional rooms)
|
||||
WHILE @i <= 50
|
||||
BEGIN
|
||||
SET @room_name = 'muc' + CAST(@i AS VARCHAR(10));
|
||||
SET @creation_time = RIGHT(REPLICATE('0', 15) + CAST(@base_time - (@i * 1000) AS VARCHAR(15)), 15);
|
||||
|
||||
INSERT INTO ofMucRoom (
|
||||
serviceID, roomID, creationDate, modificationDate, name, naturalName, description,
|
||||
lockedDate, emptyDate, canChangeSubject, maxUsers, publicRoom, moderated,
|
||||
membersOnly, canInvite, roomPassword, canDiscoverJID, logEnabled,
|
||||
retireOnDeletion, preserveHistOnDel, subject, rolesToBroadcast,
|
||||
useReservedNick, canChangeNick, canRegister, allowpm, fmucEnabled,
|
||||
fmucOutboundNode, fmucOutboundMode, fmucInboundNodes
|
||||
)
|
||||
VALUES (
|
||||
1, -- serviceID
|
||||
@i, -- roomID
|
||||
@creation_time, -- creationDate
|
||||
@creation_time, -- modificationDate
|
||||
@room_name, -- name
|
||||
@room_name, -- naturalName
|
||||
@room_name, -- description
|
||||
'000000000000000', -- lockedDate (not locked)
|
||||
@creation_time, -- emptyDate
|
||||
0, -- canChangeSubject
|
||||
30, -- maxUsers
|
||||
1, -- publicRoom
|
||||
0, -- moderated
|
||||
0, -- membersOnly
|
||||
0, -- canInvite
|
||||
NULL, -- roomPassword
|
||||
1, -- canDiscoverJID
|
||||
1, -- logEnabled
|
||||
0, -- retireOnDeletion
|
||||
1, -- preserveHistOnDel
|
||||
'', -- subject
|
||||
7, -- rolesToBroadcast
|
||||
0, -- useReservedNick
|
||||
1, -- canChangeNick
|
||||
1, -- canRegister
|
||||
0, -- allowpm
|
||||
0, -- fmucEnabled
|
||||
NULL, -- fmucOutboundNode
|
||||
NULL, -- fmucOutboundMode
|
||||
NULL -- fmucInboundNodes
|
||||
);
|
||||
|
||||
IF @i % 10 = 0
|
||||
BEGIN
|
||||
PRINT 'Created room: ' + @room_name;
|
||||
END
|
||||
|
||||
SET @i = @i + 1;
|
||||
END
|
||||
|
||||
PRINT 'Room creation complete.';
|
||||
GO
|
||||
|
||||
-- Now redistribute messages across all 50 rooms
|
||||
-- This simulates a more realistic distribution where each room has messages
|
||||
PRINT 'Redistributing messages across all 50 rooms...';
|
||||
|
||||
UPDATE ofMucConversationLog
|
||||
SET roomID = (messageID % 50) + 1;
|
||||
|
||||
PRINT 'Message redistribution complete.';
|
||||
GO
|
||||
|
||||
-- Verify
|
||||
PRINT '';
|
||||
PRINT '=== Verification ===';
|
||||
SELECT 'Total rooms: ' + CAST(COUNT(*) AS VARCHAR(10)) AS result FROM ofMucRoom;
|
||||
SELECT 'Total messages: ' + CAST(COUNT(*) AS VARCHAR(10)) AS result FROM ofMucConversationLog;
|
||||
SELECT 'Messages per room (sample):' AS result;
|
||||
SELECT TOP 10
|
||||
'Room ' + CAST(roomID AS VARCHAR(5)) + ': ' + CAST(COUNT(*) AS VARCHAR(10)) + ' messages' AS result
|
||||
FROM ofMucConversationLog
|
||||
GROUP BY roomID
|
||||
ORDER BY roomID;
|
||||
GO
|
||||
|
|
@ -0,0 +1,105 @@
|
|||
-- =============================================================================
|
||||
-- Generate Test Messages (~410,000) - MSSQL
|
||||
-- =============================================================================
|
||||
--
|
||||
-- Database: Microsoft SQL Server
|
||||
-- Compatibility: MSSQL deployments (cluster_mssql)
|
||||
--
|
||||
-- Purpose:
|
||||
-- Generates ~410,000 MUC messages distributed across 2 rooms to simulate a
|
||||
-- long-running environment experiencing slow startup due to large message
|
||||
-- history. Useful for testing MUC history loading performance.
|
||||
--
|
||||
-- Prerequisites:
|
||||
-- - Rooms with IDs 1 and 2 must exist (messages alternate between them)
|
||||
-- - Database should be initialised with Openfire schema
|
||||
--
|
||||
-- Usage:
|
||||
-- Run manually against a running MSSQL database:
|
||||
--
|
||||
-- docker exec -it mssql_server /opt/mssql-tools18/bin/sqlcmd \
|
||||
-- -S localhost -U sa -P 'YourPassword' -d openfire -C \
|
||||
-- -i /path/to/generate-test-messages.sql
|
||||
--
|
||||
-- =============================================================================
|
||||
|
||||
USE openfire;
|
||||
GO
|
||||
|
||||
SET NOCOUNT ON;
|
||||
GO
|
||||
|
||||
DECLARE @base_time BIGINT = CAST(DATEDIFF(SECOND, '1970-01-01', GETDATE()) AS BIGINT) * 1000;
|
||||
DECLARE @msg_id INT = 100;
|
||||
DECLARE @i INT = 1;
|
||||
DECLARE @room_id INT;
|
||||
DECLARE @log_time CHAR(15);
|
||||
DECLARE @batch_size INT = 1000;
|
||||
|
||||
PRINT 'Starting message generation at ' + CONVERT(VARCHAR, GETDATE(), 120);
|
||||
PRINT 'Base time: ' + CAST(@base_time AS VARCHAR(20));
|
||||
|
||||
-- Use batch inserts for better performance
|
||||
WHILE @i <= 410000
|
||||
BEGIN
|
||||
BEGIN TRANSACTION;
|
||||
|
||||
DECLARE @batch_end INT = @i + @batch_size - 1;
|
||||
IF @batch_end > 410000 SET @batch_end = 410000;
|
||||
|
||||
WHILE @i <= @batch_end
|
||||
BEGIN
|
||||
SET @room_id = (@i % 2) + 1;
|
||||
SET @log_time = RIGHT(REPLICATE('0', 15) + CAST(@base_time - (CAST(@i AS BIGINT) * 6480) AS VARCHAR(15)), 15);
|
||||
|
||||
INSERT INTO ofMucConversationLog (roomID, messageID, sender, nickname, logTime, subject, body, stanza)
|
||||
VALUES (
|
||||
@room_id,
|
||||
@msg_id,
|
||||
'user1@xmpp.localhost.example/resource',
|
||||
'User One',
|
||||
@log_time,
|
||||
NULL,
|
||||
'Test message ' + CAST(@i AS VARCHAR(10)),
|
||||
NULL
|
||||
);
|
||||
|
||||
SET @msg_id = @msg_id + 1;
|
||||
SET @i = @i + 1;
|
||||
END
|
||||
|
||||
COMMIT TRANSACTION;
|
||||
|
||||
IF (@i - 1) % 50000 = 0
|
||||
BEGIN
|
||||
PRINT 'Progress: ' + CAST(@i - 1 AS VARCHAR(10)) + ' messages inserted';
|
||||
END
|
||||
END
|
||||
|
||||
PRINT 'Message generation complete at ' + CONVERT(VARCHAR, GETDATE(), 120);
|
||||
GO
|
||||
|
||||
-- Set long history configuration using MERGE (MSSQL equivalent of ON CONFLICT)
|
||||
MERGE INTO ofMucServiceProp AS target
|
||||
USING (SELECT 1 AS serviceID, 'history.maxNumber' AS name, '1000' AS propValue) AS source
|
||||
ON target.serviceID = source.serviceID AND target.name = source.name
|
||||
WHEN MATCHED THEN UPDATE SET propValue = source.propValue
|
||||
WHEN NOT MATCHED THEN INSERT (serviceID, name, propValue) VALUES (source.serviceID, source.name, source.propValue);
|
||||
GO
|
||||
|
||||
MERGE INTO ofMucServiceProp AS target
|
||||
USING (SELECT 1 AS serviceID, 'history.type' AS name, 'number' AS propValue) AS source
|
||||
ON target.serviceID = source.serviceID AND target.name = source.name
|
||||
WHEN MATCHED THEN UPDATE SET propValue = source.propValue
|
||||
WHEN NOT MATCHED THEN INSERT (serviceID, name, propValue) VALUES (source.serviceID, source.name, source.propValue);
|
||||
GO
|
||||
|
||||
-- Ensure NO reload limit (worst case scenario)
|
||||
DELETE FROM ofProperty WHERE name = 'xmpp.muc.history.reload.limit';
|
||||
GO
|
||||
|
||||
-- Verify
|
||||
SELECT 'Total messages: ' + CAST(COUNT(*) AS VARCHAR(10)) AS result FROM ofMucConversationLog;
|
||||
SELECT 'Room ' + CAST(roomID AS VARCHAR(5)) + ': ' + CAST(COUNT(*) AS VARCHAR(10)) + ' messages' AS result
|
||||
FROM ofMucConversationLog GROUP BY roomID ORDER BY roomID;
|
||||
GO
|
||||
|
|
@ -0,0 +1,115 @@
|
|||
-- =============================================================================
|
||||
-- Create 50 MUC Rooms - PostgreSQL
|
||||
-- =============================================================================
|
||||
--
|
||||
-- Database: PostgreSQL
|
||||
-- Compatibility: All PostgreSQL deployments (simple, cluster, federation, etc.)
|
||||
--
|
||||
-- Purpose:
|
||||
-- Creates 48 additional MUC rooms (IDs 3-50) to supplement the 2 default rooms,
|
||||
-- giving a total of ~50 rooms. Also redistributes any existing messages evenly
|
||||
-- across all 50 rooms.
|
||||
--
|
||||
-- Useful for testing environments that need a moderate number of rooms with
|
||||
-- message history spread across them.
|
||||
--
|
||||
-- Prerequisites:
|
||||
-- - Rooms with IDs 1 and 2 should already exist (from 000-init-openfire.sql)
|
||||
-- - Best used after generate-test-messages.sql to have messages to redistribute
|
||||
--
|
||||
-- Usage:
|
||||
-- Option 1 - Copy to deployment's sql/ directory (runs on container start):
|
||||
--
|
||||
-- cp optional/sql/postgresql/create-50-rooms.sql simple/sql/002-create-50-rooms.sql
|
||||
-- ./start.sh
|
||||
--
|
||||
-- Option 2 - Run manually against a running database:
|
||||
--
|
||||
-- docker exec -i simple-db-1 psql -U openfire -d openfire \
|
||||
-- < optional/sql/postgresql/create-50-rooms.sql
|
||||
--
|
||||
-- =============================================================================
|
||||
|
||||
DO $$
|
||||
DECLARE
|
||||
i INTEGER;
|
||||
room_name VARCHAR(50);
|
||||
creation_time CHAR(15);
|
||||
base_time BIGINT := (EXTRACT(EPOCH FROM NOW()) * 1000)::BIGINT;
|
||||
BEGIN
|
||||
RAISE NOTICE 'Creating additional MUC rooms...';
|
||||
RAISE NOTICE 'Current time (ms): %', base_time;
|
||||
|
||||
-- Create rooms 3 through 50 (48 additional rooms)
|
||||
FOR i IN 3..50 LOOP
|
||||
room_name := 'muc' || i::TEXT;
|
||||
creation_time := LPAD((base_time - (i * 1000))::TEXT, 15, '0');
|
||||
|
||||
INSERT INTO ofmucroom (
|
||||
serviceid, roomid, creationdate, modificationdate, name, naturalname, description,
|
||||
lockeddate, emptydate, canchangesubject, maxusers, publicroom, moderated,
|
||||
membersonly, caninvite, roompassword, candiscoverjid, logenabled,
|
||||
subject, rolestobroadcast,
|
||||
usereservednick, canchangenick, canregister, allowpm, fmucenabled,
|
||||
fmucoutboundnode, fmucoutboundmode, fmucinboundnodes
|
||||
)
|
||||
VALUES (
|
||||
1, -- serviceid
|
||||
i, -- roomid
|
||||
creation_time, -- creationdate
|
||||
creation_time, -- modificationdate
|
||||
room_name, -- name
|
||||
room_name, -- naturalname
|
||||
room_name, -- description
|
||||
'000000000000000', -- lockeddate (not locked)
|
||||
creation_time, -- emptydate
|
||||
0, -- canchangesubject
|
||||
30, -- maxusers
|
||||
1, -- publicroom
|
||||
0, -- moderated
|
||||
0, -- membersonly
|
||||
0, -- caninvite
|
||||
NULL, -- roompassword
|
||||
1, -- candiscoverjid
|
||||
1, -- logenabled
|
||||
'', -- subject
|
||||
7, -- rolestobroadcast
|
||||
0, -- usereservednick
|
||||
1, -- canchangenick
|
||||
1, -- canregister
|
||||
0, -- allowpm
|
||||
0, -- fmucenabled
|
||||
NULL, -- fmucoutboundnode
|
||||
NULL, -- fmucoutboundmode
|
||||
NULL -- fmucinboundnodes
|
||||
);
|
||||
|
||||
IF i % 10 = 0 THEN
|
||||
RAISE NOTICE 'Created room: %', room_name;
|
||||
END IF;
|
||||
END LOOP;
|
||||
|
||||
RAISE NOTICE 'Room creation complete.';
|
||||
END $$;
|
||||
|
||||
-- Now redistribute messages across all 50 rooms
|
||||
-- This simulates a more realistic distribution where each room has messages
|
||||
DO $$
|
||||
BEGIN
|
||||
RAISE NOTICE 'Redistributing messages across all 50 rooms...';
|
||||
|
||||
UPDATE ofmucconversationlog
|
||||
SET roomid = (messageid % 50) + 1;
|
||||
|
||||
RAISE NOTICE 'Message redistribution complete.';
|
||||
END $$;
|
||||
|
||||
-- Verify
|
||||
SELECT 'Total rooms: ' || COUNT(*)::TEXT AS result FROM ofmucroom;
|
||||
SELECT 'Total messages: ' || COUNT(*)::TEXT AS result FROM ofmucconversationlog;
|
||||
SELECT 'Messages per room (sample):' AS result;
|
||||
SELECT 'Room ' || roomid || ': ' || COUNT(*)::TEXT || ' messages' AS result
|
||||
FROM ofmucconversationlog
|
||||
GROUP BY roomid
|
||||
ORDER BY roomid
|
||||
LIMIT 10;
|
||||
|
|
@ -1,25 +1,29 @@
|
|||
-- =============================================================================
|
||||
-- Generate Test Data: Slow Startup Issue Recreation
|
||||
-- Generate Test Messages (~410,000) - PostgreSQL
|
||||
-- =============================================================================
|
||||
--
|
||||
-- Compatibility: all deployments (simple, cluster, federation, cluster_with_federation, proxy)
|
||||
-- Database: PostgreSQL
|
||||
-- Compatibility: All PostgreSQL deployments (simple, cluster, federation, etc.)
|
||||
--
|
||||
-- Purpose:
|
||||
-- Generates ~410,000 MUC messages to simulate a long-running environment
|
||||
-- experiencing slow startup due to large message history.
|
||||
-- Generates ~410,000 MUC messages distributed across 2 rooms to simulate a
|
||||
-- long-running environment experiencing slow startup due to large message
|
||||
-- history. Useful for testing MUC history loading performance.
|
||||
--
|
||||
-- Prerequisites:
|
||||
-- - Rooms with IDs 1 and 2 must exist (messages alternate between them)
|
||||
-- - Use with 000-init-openfire.sql which creates default rooms
|
||||
--
|
||||
-- Usage:
|
||||
-- 1. Copy this file to your deployment's sql/ directory:
|
||||
--
|
||||
-- cp optional/sql/001-generate-test-data.sql simple/sql/
|
||||
--
|
||||
-- 2. Restart containers (or start fresh if DB already initialised):
|
||||
-- Option 1 - Copy to deployment's sql/ directory (runs on container start):
|
||||
--
|
||||
-- cp optional/sql/postgresql/generate-test-messages.sql simple/sql/001-generate-test-messages.sql
|
||||
-- ./start.sh
|
||||
--
|
||||
-- Alternatively, run manually against a running database:
|
||||
-- Option 2 - Run manually against a running database:
|
||||
--
|
||||
-- docker exec -i simple-db-1 psql -U openfire -d openfire < optional/sql/001-generate-test-data.sql
|
||||
-- docker exec -i simple-db-1 psql -U openfire -d openfire \
|
||||
-- < optional/sql/postgresql/generate-test-messages.sql
|
||||
--
|
||||
-- =============================================================================
|
||||
|
||||
|
|
@ -0,0 +1,128 @@
|
|||
-- =============================================================================
|
||||
-- Performance Test: 10,000 Minimal MUC Rooms - PostgreSQL
|
||||
-- =============================================================================
|
||||
--
|
||||
-- Database: PostgreSQL
|
||||
-- Compatibility: All PostgreSQL deployments (simple, cluster, federation, etc.)
|
||||
--
|
||||
-- Purpose:
|
||||
-- Creates 10,000 MUC rooms with minimal data for testing parallel loading
|
||||
-- performance at scale. Each room includes:
|
||||
-- - Basic room metadata
|
||||
-- - Single owner affiliation
|
||||
-- - No message history (focus on room loading, not history)
|
||||
--
|
||||
-- This is ideal for testing MUC room loading performance when you need many
|
||||
-- rooms but don't need message history to slow things down.
|
||||
--
|
||||
-- Note:
|
||||
-- This script replaces any existing rooms (uses room IDs 1-10000).
|
||||
-- For a smaller, more realistic dataset with messages and affiliations,
|
||||
-- see performance-test-200-rooms-with-data.sql instead.
|
||||
--
|
||||
-- Usage:
|
||||
-- Option 1 - Copy to deployment's sql/ directory (runs on container start):
|
||||
--
|
||||
-- cp optional/sql/postgresql/performance-test-10000-rooms.sql simple/sql/001-perf-rooms.sql
|
||||
-- ./start.sh
|
||||
--
|
||||
-- Option 2 - Run manually against a running database:
|
||||
--
|
||||
-- docker exec -i simple-db-1 psql -U openfire -d openfire \
|
||||
-- < optional/sql/postgresql/performance-test-10000-rooms.sql
|
||||
--
|
||||
-- =============================================================================
|
||||
|
||||
DO $$
|
||||
DECLARE
|
||||
base_time BIGINT := (EXTRACT(EPOCH FROM NOW()) * 1000)::BIGINT;
|
||||
batch_size INTEGER := 1000;
|
||||
i INTEGER;
|
||||
BEGIN
|
||||
RAISE NOTICE 'Creating 10,000 performance test MUC rooms...';
|
||||
RAISE NOTICE 'Current time (ms): %', base_time;
|
||||
RAISE NOTICE 'Using batch inserts for efficiency...';
|
||||
|
||||
-- Create rooms 1 through 10,000 using generate_series for efficiency
|
||||
-- Insert rooms in batches to avoid memory issues
|
||||
FOR i IN 0..9 LOOP
|
||||
INSERT INTO ofmucroom (
|
||||
serviceid, roomid, creationdate, modificationdate, name, naturalname, description,
|
||||
lockeddate, emptydate, canchangesubject, maxusers, publicroom, moderated,
|
||||
membersonly, caninvite, roompassword, candiscoverjid, logenabled,
|
||||
subject, rolestobroadcast,
|
||||
usereservednick, canchangenick, canregister, allowpm, fmucenabled,
|
||||
fmucoutboundnode, fmucoutboundmode, fmucinboundnodes
|
||||
)
|
||||
SELECT
|
||||
1, -- serviceid
|
||||
room_num, -- roomid
|
||||
LPAD((base_time - (room_num * 10000))::TEXT, 15, '0'), -- creationdate
|
||||
LPAD((base_time - (room_num * 10000))::TEXT, 15, '0'), -- modificationdate
|
||||
'perftest' || room_num::TEXT, -- name
|
||||
'Performance Test Room ' || room_num::TEXT, -- naturalname
|
||||
'Test room for parallel loading performance testing', -- description
|
||||
'000000000000000', -- lockeddate (not locked)
|
||||
LPAD((base_time - (room_num * 10000))::TEXT, 15, '0'), -- emptydate
|
||||
1, -- canchangesubject
|
||||
50, -- maxusers
|
||||
1, -- publicroom
|
||||
0, -- moderated
|
||||
0, -- membersonly
|
||||
1, -- caninvite
|
||||
NULL, -- roompassword
|
||||
1, -- candiscoverjid
|
||||
1, -- logenabled
|
||||
'Welcome to performance test room ' || room_num::TEXT, -- subject
|
||||
7, -- rolestobroadcast (all roles)
|
||||
0, -- usereservednick
|
||||
1, -- canchangenick
|
||||
1, -- canregister
|
||||
1, -- allowpm (anyone)
|
||||
0, -- fmucenabled
|
||||
NULL, -- fmucoutboundnode
|
||||
NULL, -- fmucoutboundmode
|
||||
NULL -- fmucinboundnodes
|
||||
FROM generate_series((i * batch_size) + 1, (i + 1) * batch_size) AS room_num;
|
||||
|
||||
RAISE NOTICE 'Batch %: Inserted rooms % to %', i + 1, (i * batch_size) + 1, (i + 1) * batch_size;
|
||||
END LOOP;
|
||||
|
||||
RAISE NOTICE 'Room creation complete. Creating affiliations...';
|
||||
|
||||
-- Create owner affiliations in batches (one owner per room)
|
||||
FOR i IN 0..9 LOOP
|
||||
INSERT INTO ofmucaffiliation (roomid, jid, affiliation)
|
||||
SELECT
|
||||
room_num,
|
||||
'owner' || room_num::TEXT || '@xmpp.localhost.example',
|
||||
10 -- owner affiliation
|
||||
FROM generate_series((i * batch_size) + 1, (i + 1) * batch_size) AS room_num;
|
||||
|
||||
RAISE NOTICE 'Batch %: Created affiliations for rooms % to %', i + 1, (i * batch_size) + 1, (i + 1) * batch_size;
|
||||
END LOOP;
|
||||
|
||||
RAISE NOTICE 'Performance test room creation complete.';
|
||||
RAISE NOTICE 'Total rooms created: 10,000';
|
||||
RAISE NOTICE 'Total affiliations created: %', (SELECT COUNT(*) FROM ofmucaffiliation WHERE roomid BETWEEN 1 AND 10000);
|
||||
END $$;
|
||||
|
||||
-- Set history configuration for the service
|
||||
INSERT INTO ofmucserviceprop (serviceid, name, propvalue)
|
||||
VALUES (1, 'history.maxNumber', '100')
|
||||
ON CONFLICT (serviceid, name) DO UPDATE SET propvalue = '100';
|
||||
|
||||
INSERT INTO ofmucserviceprop (serviceid, name, propvalue)
|
||||
VALUES (1, 'history.type', 'number')
|
||||
ON CONFLICT (serviceid, name) DO UPDATE SET propvalue = 'number';
|
||||
|
||||
-- Verify data
|
||||
SELECT 'Total rooms: ' || COUNT(*)::TEXT AS summary FROM ofmucroom;
|
||||
SELECT 'Total affiliations: ' || COUNT(*)::TEXT AS summary FROM ofmucaffiliation;
|
||||
SELECT 'Total messages: ' || COUNT(*)::TEXT AS summary FROM ofmucconversationlog;
|
||||
SELECT 'Sample - Messages per room (first 10):' AS summary;
|
||||
SELECT 'Room ' || roomid || ': ' || COUNT(*)::TEXT || ' messages' AS detail
|
||||
FROM ofmucconversationlog
|
||||
WHERE roomid <= 10
|
||||
GROUP BY roomid
|
||||
ORDER BY roomid;
|
||||
|
|
@ -0,0 +1,164 @@
|
|||
-- =============================================================================
|
||||
-- Performance Test: 200 Rooms with Realistic Data - PostgreSQL
|
||||
-- =============================================================================
|
||||
--
|
||||
-- Database: PostgreSQL
|
||||
-- Compatibility: All PostgreSQL deployments (simple, cluster, federation, etc.)
|
||||
--
|
||||
-- Purpose:
|
||||
-- Creates 200 MUC rooms with realistic data for testing parallel loading
|
||||
-- performance. Each room includes:
|
||||
-- - Varied affiliations (1 owner, 1-2 admins, 3-5 members)
|
||||
-- - Message history (100-500 messages per room, ~60,000 total)
|
||||
-- - Realistic metadata
|
||||
--
|
||||
-- This is ideal when you need a realistic dataset with varied affiliations
|
||||
-- and message history to test how Openfire handles loading complete room data.
|
||||
--
|
||||
-- Note:
|
||||
-- This script replaces any existing rooms (uses room IDs 1-200).
|
||||
-- For high-volume room testing without message history, see
|
||||
-- performance-test-10000-rooms.sql instead.
|
||||
--
|
||||
-- Usage:
|
||||
-- Option 1 - Copy to deployment's sql/ directory (runs on container start):
|
||||
--
|
||||
-- cp optional/sql/postgresql/performance-test-200-rooms-with-data.sql simple/sql/001-perf-rooms.sql
|
||||
-- ./start.sh
|
||||
--
|
||||
-- Option 2 - Run manually against a running database:
|
||||
--
|
||||
-- docker exec -i simple-db-1 psql -U openfire -d openfire \
|
||||
-- < optional/sql/postgresql/performance-test-200-rooms-with-data.sql
|
||||
--
|
||||
-- =============================================================================
|
||||
|
||||
DO $$
|
||||
DECLARE
|
||||
i INTEGER;
|
||||
j INTEGER;
|
||||
room_name VARCHAR(50);
|
||||
creation_time CHAR(15);
|
||||
base_time BIGINT := (EXTRACT(EPOCH FROM NOW()) * 1000)::BIGINT;
|
||||
msg_id INTEGER := 1000000;
|
||||
room_id_val INTEGER;
|
||||
message_count INTEGER;
|
||||
affiliation_count INTEGER;
|
||||
BEGIN
|
||||
RAISE NOTICE 'Creating 200 performance test MUC rooms...';
|
||||
RAISE NOTICE 'Current time (ms): %', base_time;
|
||||
|
||||
-- Create rooms 1 through 200
|
||||
FOR i IN 1..200 LOOP
|
||||
room_name := 'perftest' || i::TEXT;
|
||||
creation_time := LPAD((base_time - (i * 10000))::TEXT, 15, '0');
|
||||
|
||||
INSERT INTO ofmucroom (
|
||||
serviceid, roomid, creationdate, modificationdate, name, naturalname, description,
|
||||
lockeddate, emptydate, canchangesubject, maxusers, publicroom, moderated,
|
||||
membersonly, caninvite, roompassword, candiscoverjid, logenabled,
|
||||
subject, rolestobroadcast,
|
||||
usereservednick, canchangenick, canregister, allowpm, fmucenabled,
|
||||
fmucoutboundnode, fmucoutboundmode, fmucinboundnodes
|
||||
)
|
||||
VALUES (
|
||||
1, -- serviceid
|
||||
i, -- roomid
|
||||
creation_time, -- creationdate
|
||||
creation_time, -- modificationdate
|
||||
room_name, -- name
|
||||
'Performance Test Room ' || i::TEXT, -- naturalname
|
||||
'Test room for parallel loading performance testing', -- description
|
||||
'000000000000000', -- lockeddate (not locked)
|
||||
creation_time, -- emptydate
|
||||
1, -- canchangesubject
|
||||
50, -- maxusers
|
||||
1, -- publicroom
|
||||
0, -- moderated
|
||||
0, -- membersonly
|
||||
1, -- caninvite
|
||||
NULL, -- roompassword
|
||||
1, -- candiscoverjid
|
||||
1, -- logenabled
|
||||
'Welcome to performance test room ' || i::TEXT, -- subject
|
||||
7, -- rolestobroadcast (all roles)
|
||||
0, -- usereservednick
|
||||
1, -- canchangenick
|
||||
1, -- canregister
|
||||
1, -- allowpm (anyone)
|
||||
0, -- fmucenabled
|
||||
NULL, -- fmucoutboundnode
|
||||
NULL, -- fmucoutboundmode
|
||||
NULL -- fmucinboundnodes
|
||||
)
|
||||
RETURNING roomid INTO room_id_val;
|
||||
|
||||
-- Add affiliations for this room
|
||||
-- Each room gets: 1 owner, 1-2 admins, 3-5 members
|
||||
affiliation_count := 3 + (i % 3); -- 3-5 affiliations per room
|
||||
|
||||
-- Owner
|
||||
INSERT INTO ofmucaffiliation (roomid, jid, affiliation)
|
||||
VALUES (room_id_val, 'owner' || i::TEXT || '@xmpp.localhost.example', 10);
|
||||
|
||||
-- Admin(s)
|
||||
FOR j IN 1..(1 + (i % 2)) LOOP
|
||||
INSERT INTO ofmucaffiliation (roomid, jid, affiliation)
|
||||
VALUES (room_id_val, 'admin' || i::TEXT || '-' || j::TEXT || '@xmpp.localhost.example', 20);
|
||||
END LOOP;
|
||||
|
||||
-- Members
|
||||
FOR j IN 1..(3 + (i % 3)) LOOP
|
||||
INSERT INTO ofmucaffiliation (roomid, jid, affiliation)
|
||||
VALUES (room_id_val, 'member' || i::TEXT || '-' || j::TEXT || '@xmpp.localhost.example', 30);
|
||||
END LOOP;
|
||||
|
||||
-- Add message history for this room
|
||||
-- Each room gets 100-500 messages (varies by room number)
|
||||
message_count := 100 + ((i * 37) % 401); -- Pseudo-random 100-500
|
||||
|
||||
FOR j IN 1..message_count LOOP
|
||||
INSERT INTO ofmucconversationlog (roomid, messageid, sender, nickname, logtime, subject, body, stanza)
|
||||
VALUES (
|
||||
room_id_val,
|
||||
msg_id,
|
||||
'user' || ((j % 10) + 1)::TEXT || '@xmpp.localhost.example/resource',
|
||||
'User ' || ((j % 10) + 1)::TEXT,
|
||||
LPAD((base_time - (j::BIGINT * 60000))::TEXT, 15, '0'), -- 1 minute intervals
|
||||
CASE WHEN j % 50 = 1 THEN 'Discussion topic ' || (j/50 + 1)::TEXT ELSE NULL END,
|
||||
'Test message ' || j::TEXT || ' in room ' || room_name,
|
||||
NULL
|
||||
);
|
||||
msg_id := msg_id + 1;
|
||||
END LOOP;
|
||||
|
||||
IF i % 20 = 0 THEN
|
||||
RAISE NOTICE 'Created room % with % affiliations and % messages', room_name, affiliation_count, message_count;
|
||||
END IF;
|
||||
END LOOP;
|
||||
|
||||
RAISE NOTICE 'Performance test room creation complete.';
|
||||
RAISE NOTICE 'Total rooms created: 200';
|
||||
RAISE NOTICE 'Total affiliations created: %', (SELECT COUNT(*) FROM ofmucaffiliation);
|
||||
RAISE NOTICE 'Total messages created: %', (SELECT COUNT(*) FROM ofmucconversationlog);
|
||||
END $$;
|
||||
|
||||
-- Set history configuration for the service
|
||||
INSERT INTO ofmucserviceprop (serviceid, name, propvalue)
|
||||
VALUES (1, 'history.maxNumber', '100')
|
||||
ON CONFLICT (serviceid, name) DO UPDATE SET propvalue = '100';
|
||||
|
||||
INSERT INTO ofmucserviceprop (serviceid, name, propvalue)
|
||||
VALUES (1, 'history.type', 'number')
|
||||
ON CONFLICT (serviceid, name) DO UPDATE SET propvalue = 'number';
|
||||
|
||||
-- Verify data
|
||||
SELECT 'Total rooms: ' || COUNT(*)::TEXT AS summary FROM ofmucroom;
|
||||
SELECT 'Total affiliations: ' || COUNT(*)::TEXT AS summary FROM ofmucaffiliation;
|
||||
SELECT 'Total messages: ' || COUNT(*)::TEXT AS summary FROM ofmucconversationlog;
|
||||
SELECT 'Sample - Messages per room (first 10):' AS summary;
|
||||
SELECT 'Room ' || roomid || ': ' || COUNT(*)::TEXT || ' messages' AS detail
|
||||
FROM ofmucconversationlog
|
||||
WHERE roomid <= 10
|
||||
GROUP BY roomid
|
||||
ORDER BY roomid;
|
||||
|
|
@ -0,0 +1,44 @@
|
|||
-- =============================================================================
|
||||
-- Set MUC Room Loading Worker Count - PostgreSQL
|
||||
-- =============================================================================
|
||||
--
|
||||
-- Database: PostgreSQL
|
||||
-- Compatibility: All PostgreSQL deployments (simple, cluster, federation, etc.)
|
||||
--
|
||||
-- Purpose:
|
||||
-- Sets the xmpp.muc.loading.workers property in the database.
|
||||
-- This controls how many parallel workers are used to load MUC rooms
|
||||
-- from the database during Openfire startup.
|
||||
--
|
||||
-- Usage:
|
||||
-- -- For sequential loading (1 worker):
|
||||
-- docker exec -i openfire-db-1 psql -U openfire -d openfire <<EOF
|
||||
-- DELETE FROM ofproperty WHERE name = 'xmpp.muc.loading.workers';
|
||||
-- INSERT INTO ofproperty (name, propvalue) VALUES ('xmpp.muc.loading.workers', '1');
|
||||
-- EOF
|
||||
--
|
||||
-- -- For parallel loading (3 workers):
|
||||
-- docker exec -i openfire-db-1 psql -U openfire -d openfire <<EOF
|
||||
-- DELETE FROM ofproperty WHERE name = 'xmpp.muc.loading.workers';
|
||||
-- INSERT INTO ofproperty (name, propvalue) VALUES ('xmpp.muc.loading.workers', '3');
|
||||
-- EOF
|
||||
--
|
||||
-- -- For parallel loading (5 workers):
|
||||
-- docker exec -i openfire-db-1 psql -U openfire -d openfire <<EOF
|
||||
-- DELETE FROM ofproperty WHERE name = 'xmpp.muc.loading.workers';
|
||||
-- INSERT INTO ofproperty (name, propvalue) VALUES ('xmpp.muc.loading.workers', '5');
|
||||
-- EOF
|
||||
--
|
||||
-- Note: The value will be read during Openfire startup, so you need to
|
||||
-- restart Openfire after changing this property.
|
||||
--
|
||||
-- =============================================================================
|
||||
|
||||
-- This file is a template - actual values are set dynamically by the test script
|
||||
-- Default to 1 worker (sequential) if run standalone
|
||||
DELETE FROM ofproperty WHERE name = 'xmpp.muc.loading.workers';
|
||||
INSERT INTO ofproperty (name, propvalue) VALUES ('xmpp.muc.loading.workers', '1');
|
||||
|
||||
SELECT 'Property set: ' || name || ' = ' || propvalue AS result
|
||||
FROM ofproperty
|
||||
WHERE name = 'xmpp.muc.loading.workers';
|
||||
Loading…
Reference in New Issue