Skip to content

feat: add user scrambler for demoing cloned sites (#175) - #231

Open
faisalahammad wants to merge 1 commit into
bordoni:mainfrom
faisalahammad:fix/175-user-scrambler
Open

feat: add user scrambler for demoing cloned sites (#175)#231
faisalahammad wants to merge 1 commit into
bordoni:mainfrom
faisalahammad:fix/175-user-scrambler

Conversation

@faisalahammad

Copy link
Copy Markdown
Contributor

Summary

Adds a new FakerPress > Scramble admin page that replaces the names and emails of existing (real) users with realistic fake data. This lets a site owner clone their real site and demo it without exposing real customer names or emails, as requested in #175.

Closes #175

Changes

New admin view: Scramble_View

Modeled on the existing destructive "erase all" flow in Settings_View (same nonce + typed confirmation phrase + capability pattern), since scrambling real data is irreversible.

Why a plain admin POST and not a REST endpoint or a Module: every existing module is insert-only (they all call wp_insert_*), and Module::fetch() only returns FakerPress-flagged records, never real ones. A scrambler is the opposite: it must find and update real records. Routing it through the module set() -> generate() -> save() lifecycle would mean stubbing fetch/delete/get_slug just to override filter_save_response, so it is simpler and safer to keep it as a standalone admin action.

What gets scrambled

Per eligible user:

  • first_name, last_name, display_name (set to "First Last"), nickname, and user_email (a fake @example.* address).

Intentionally left untouched:

  • user_login (changing it breaks logins, and display_name is what shows publicly)
  • user_pass (so no password reset emails fire)

Safety

  • Gated by manage_options and a typed phrase (Scramble or Scramble!).
  • The admin running the action is always excluded.
  • FakerPress-generated users are skipped (they carry fakerpress_flag and are already fake).
  • Each scrambled user is marked with an internal _fakerpress_scrambled meta flag, so re-runs are idempotent.
  • Batch cap of 500 users per run with a notice to run again if more remain.
  • Email collisions (the user_email unique index) are retried up to 5 times; if all fail the user is skipped and stays eligible next run.

Registration

One line added to Admin/View/Factory.php::get_all() to register the view (views register their own admin menu via hook()).

Before:

$views_classes = [
    Attachment_View::class,
    Comment_View::class,
    Post_View::class,
    Settings_View::class,
    Error_View::class,
    Changelog_View::class,
    Term_View::class,
    User_View::class,
];

After:

$views_classes = [
    Attachment_View::class,
    Comment_View::class,
    Post_View::class,
    Settings_View::class,
    Scramble_View::class,
    Error_View::class,
    Changelog_View::class,
    Term_View::class,
    User_View::class,
];

Testing

Test 1: page appears

  1. Activate the plugin, go to WP Admin > FakerPress > Scramble.
    Result: a "Scramble Users" page with one text field and a "Scramble!" button.

Test 2: wrong phrase does nothing

  1. Have 2-3 real users besides the logged-in admin.
  2. On the Scramble page, type hello and click Scramble!.
    Result: a red error notice "The verification to scramble the users has failed...", no user data changes.

Test 3: correct phrase scrambles eligible users

  1. Type Scramble and click Scramble!.
    Result: green success notice "Successfully scrambled N users". In Users, non-admin users now have fake names/emails; the logged-in admin's row is unchanged; user_login slugs are unchanged.

Test 4: idempotent re-run

  1. Go back to the Scramble page, type Scramble, click again.
    Result: "No users were available to scramble..." Already-scrambled users are not touched again.

Test 5: FakerPress-generated users are skipped

  1. Generate fake users via FakerPress > Users, then run the Scramble action.
    Result: the generated users keep their original fake data (they carry fakerpress_flag).

Environment: WordPress 6.x, PHP 8.1+. PHPCS clean on the changed files (only the inherent meta_query/exclude warnings remain).

Notes

  • This first cut targets users only, as that is the core ask in feature request - content scrambler #175. Posts and comments can follow the same pattern in a later PR once this lands.
  • Irreversible by design (matches the existing Settings erase-all behavior); relies on a database backup before running. No restore path is included.

Adds a FakerPress > Scramble admin page that replaces the names and
emails of existing users with realistic fake data, so a site owner can
demo a clone of their real site without exposing real customer info.

- New Scramble_View, modeled on the Settings erase-all flow: gated by a
  typed confirmation phrase, manage_options capability, and a nonce.
- Queries real users with its own WP_User_Query, excluding the current
  admin, already-scrambled users, and FakerPress-generated users.
- Updates first_name, last_name, display_name, nickname and user_email
  via wp_update_user; leaves user_login and user_pass intact so logins
  keep working and no password reset emails fire.
- Marks each scrambled user with an internal _fakerpress_scrambled meta
  flag so re-runs are idempotent. Batch cap of 500 users per run.

Closes bordoni#175
@faisalahammad

Copy link
Copy Markdown
Contributor Author

The two failing checks (PHP Code Standards and JS Build & Lint) are not caused by this PR. They fail the same way on the main branch. See the main run from 2026-07-16, the day before this PR run: https://github.com/bordoni/fakerpress/actions/runs/29510943293

PHP Code Standards runs phpcs over the whole src/ tree with no diff filter, so it exits on pre-existing errors in files this PR does not touch (Field.php, Menu.php, Provider files, and every *_View.php flagged for a missing line-1 file docblock).

The files this PR adds or changes are clean:

  • Scramble_View.php: 0 errors. The 2 warnings (meta_query and exclude) are inherent to querying users that lack two meta flags. They are non-blocking (warnings never raise the exit code) and there is no clean core alternative.
  • scramble.php template: 0 violations.
  • Factory.php: the only change is one array entry. The warnings on that file pre-date this PR.

JS Build & Lint reports 628 errors, all in field.dependency.js, fields.js, qs.js, and select2.js. This PR adds no JavaScript.

WPUnit passes on PHP 8.1, 8.2, and 8.3, so the feature itself works.

So nothing in this PR needs to change to fix CI. The red checks are repo-wide debt on main that would be better handled in a separate cleanup PR.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feature request - content scrambler

1 participant