You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

7.1 KiB

Demo branch setup (debrand)

This branch is a white-label demo. fpsms_demo is a full copy of the live database fpsmsdb, then rewritten in place so names, codes, and other identifying values become placeholders. Row counts, ids, statuses, quantities, and dates stay. It must not read or write fpsmsdb, and it must not call the live M18 system.

Check out debrand in both repositories:

  • FPSMS-backend
  • FPSMS-frontend

Do not merge this branch. Do not start it with db-local, prod, or db-toa.

What you get

Site Frontend on port 3000, API on port 8090
Spring profile db-demo
Database fpsms_demo on 127.0.0.1:3306
App login demo / Demo2026!
Also demo.stock / Demo2026! (倉務), demo.prod / Demo2026! (出品)

demo is an existing admin user, renamed. Every copied password is reset to Demo2026!. demo.stock and demo.prod are renamed only when a stock-only user and a production-only user already exist. Floors are A/F (was 2/F) and B/F (was 4/F). Item codes look like ITEM-12, shops like SHOP-3, lots like LOT-9.

1. Stop anything already on port 8090

The frontend on this branch calls http://localhost:8090/api. If a normal backend is already listening there, it is the live database. Stop that process before starting the demo.

2. Copy production into fpsms_demo, then replace identifying values

Liquibase changesets in this repo name the schema fpsmsdb. Do not run them against the live database.

Use the local root account from application-db-local.yml only for this copy. Load structure and rows, including Liquibase history, then run the anonymize script. The script updates existing rows. It does not delete them. It refuses to run unless the current database is fpsms_demo, and it refuses to run again after settings.name = DEMO.anonymized.v1 is set.

mysql -h127.0.0.1 -P3306 -uroot -p -e \
  "DROP DATABASE IF EXISTS fpsms_demo; CREATE DATABASE fpsms_demo CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;"

mysqldump --routines --triggers -h127.0.0.1 -P3306 -uroot -p fpsmsdb \
  > /tmp/fpsms_demo_copy.sql

mysql -h127.0.0.1 -P3306 -uroot -p fpsms_demo < /tmp/fpsms_demo_copy.sql

mysql -h127.0.0.1 -P3306 -uroot -p fpsms_demo \
  < scripts/anonymize_demo_copy.sql

In MySQL Workbench the default query timeout is 30 seconds. A full copy takes longer, and Workbench then reports error 2013 even though the server may still be working. Before running the script: MySQL Workbench → Settings → SQL Editor → DBMS connection read timeout interval = 3600. Reconnect, select fpsms_demo, and run the whole file.

Dropping fpsms_demo removes a previous demo copy only. Do not point that DROP at fpsmsdb.

After the script, a sample of items.code, shop.name, inventory_lot.lotNo, user.username, and floor store_id values should be placeholders, and SELECT COUNT(*) on those tables should match the production copy. Every user password is Demo2026!.

3. Create a login that cannot see fpsmsdb

application-db-demo.yml connects as fpsms_demo / FpsmsDemoOnly2026. That account is allowed to use fpsms_demo only.

mysql -h127.0.0.1 -P3306 -uroot -p <<'SQL'
CREATE USER IF NOT EXISTS 'fpsms_demo'@'127.0.0.1' IDENTIFIED BY 'FpsmsDemoOnly2026';
CREATE USER IF NOT EXISTS 'fpsms_demo'@'localhost' IDENTIFIED BY 'FpsmsDemoOnly2026';
ALTER USER 'fpsms_demo'@'127.0.0.1' IDENTIFIED BY 'FpsmsDemoOnly2026';
ALTER USER 'fpsms_demo'@'localhost' IDENTIFIED BY 'FpsmsDemoOnly2026';
GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, REFERENCES, INDEX, ALTER,
      CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, CREATE VIEW, SHOW VIEW,
      CREATE ROUTINE, ALTER ROUTINE, EVENT, TRIGGER
  ON fpsms_demo.* TO 'fpsms_demo'@'127.0.0.1';
GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, REFERENCES, INDEX, ALTER,
      CREATE TEMPORARY TABLES, LOCK TABLES, EXECUTE, CREATE VIEW, SHOW VIEW,
      CREATE ROUTINE, ALTER ROUTINE, EVENT, TRIGGER
  ON fpsms_demo.* TO 'fpsms_demo'@'localhost';
FLUSH PRIVILEGES;
SQL

Confirm the wall before starting the app. The first command must fail with MySQL error 1142. The second must succeed.

mysql -h127.0.0.1 -P3306 -ufpsms_demo -pFpsmsDemoOnly2026 -e "SELECT COUNT(*) FROM fpsmsdb.user;"
mysql -h127.0.0.1 -P3306 -ufpsms_demo -pFpsmsDemoOnly2026 -D fpsms_demo -e "SELECT COUNT(*) FROM user;"

Do not put root back into application-db-demo.yml. If this login can read fpsmsdb, the demo profile refuses to start. That refusal is the point.

4. Start the backend

JDK 17. From FPSMS-backend, on branch debrand:

./gradlew bootRun --args='--spring.profiles.active=db-demo'

Startup does not insert sample rows. It refuses to start unless DEMO.anonymized.v1 is present, so a raw production copy cannot be served. Dates stay on the days they had in the copy.

In the log, expect:

Demo database login cannot read live schema fpsmsdb (MySQL error 1142).

Do not expect Token updated. That line means the process asked the live M18 server for a token.

M18 screens are hidden. Calling them directly returns 403, for example GET /api/m18/test/po-by-code.

5. Start the frontend

From FPSMS-frontend, on branch debrand:

npm install
npm run dev

Open http://localhost:3000. .env.development and .env.production on this branch both point at port 8090 on this machine. Do not point NEXT_PUBLIC_API_URL at 10.10.0.81 or any other live server.

Sign in as demo / Demo2026!.

If startup fails

Log What to do
Can read live schema fpsmsdb The datasource user is too powerful. Recreate fpsms_demo as in step 3. Do not bypass the check.
Access denied for fpsms_demo The user or password does not match application-db-demo.yml, or the grants were not flushed.
Liquibase tries to alter fpsmsdb The changelog tables were not copied into fpsms_demo. Repeat step 2. With the restricted login this should fail closed, not change live data.
has not been anonymized Run scripts/anonymize_demo_copy.sql against fpsms_demo. Do not start the app on the raw copy.
Port 8090 already in use Stop the other backend. Do not point the demo frontend at it.