@memberjunction/cli 5.47.0 → 5.48.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/oclif.manifest.json +802 -802
  2. package/package.json +17 -17
@@ -2911,52 +2911,187 @@
2911
2911
  "index.js"
2912
2912
  ]
2913
2913
  },
2914
- "sync:file-reset": {
2914
+ "test:compare": {
2915
2915
  "aliases": [],
2916
- "args": {},
2917
- "description": "Reset file metadata sections",
2916
+ "args": {
2917
+ "runId1": {
2918
+ "description": "First test run ID to compare",
2919
+ "name": "runId1",
2920
+ "required": false
2921
+ },
2922
+ "runId2": {
2923
+ "description": "Second test run ID to compare",
2924
+ "name": "runId2",
2925
+ "required": false
2926
+ }
2927
+ },
2928
+ "description": "Compare test runs for regression detection",
2918
2929
  "examples": [
2919
2930
  "<%= config.bin %> <%= command.id %>",
2920
- "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
2921
- "<%= config.bin %> <%= command.id %> --sections=\"dependencies,references\"",
2922
- "<%= config.bin %> <%= command.id %> --all"
2931
+ "<%= config.bin %> <%= command.id %> --latest",
2932
+ "<%= config.bin %> <%= command.id %> <run-id-1> <run-id-2>",
2933
+ "<%= config.bin %> <%= command.id %> -v 5.17.0 -v 5.18.0",
2934
+ "<%= config.bin %> <%= command.id %> -c abc1234 -c def5678",
2935
+ "<%= config.bin %> <%= command.id %> --from-json baseline.json latest.json",
2936
+ "<%= config.bin %> <%= command.id %> --latest --format=markdown --output=report.md"
2923
2937
  ],
2924
2938
  "flags": {
2925
- "dir": {
2926
- "description": "Specific entity directory to reset",
2927
- "name": "dir",
2939
+ "version": {
2940
+ "char": "v",
2941
+ "description": "Compare runs by version",
2942
+ "name": "version",
2928
2943
  "hasDynamicHelp": false,
2929
- "multiple": false,
2944
+ "multiple": true,
2930
2945
  "type": "option"
2931
2946
  },
2932
- "sections": {
2933
- "description": "Comma-separated list of sections to reset (dependencies,references,related,lookup)",
2934
- "name": "sections",
2947
+ "commit": {
2948
+ "char": "c",
2949
+ "description": "Compare runs by git commit",
2950
+ "name": "commit",
2935
2951
  "hasDynamicHelp": false,
2936
- "multiple": false,
2952
+ "multiple": true,
2937
2953
  "type": "option"
2938
2954
  },
2939
- "all": {
2940
- "description": "Reset all metadata sections",
2941
- "name": "all",
2955
+ "diff-only": {
2956
+ "description": "Show only differences",
2957
+ "name": "diff-only",
2942
2958
  "allowNo": false,
2943
2959
  "type": "boolean"
2944
2960
  },
2945
- "dry-run": {
2946
- "description": "Show what would be reset without actually resetting",
2947
- "name": "dry-run",
2961
+ "latest": {
2962
+ "char": "l",
2963
+ "description": "Compare the two most recent completed suite runs",
2964
+ "name": "latest",
2948
2965
  "allowNo": false,
2949
2966
  "type": "boolean"
2950
2967
  },
2951
- "force": {
2952
- "description": "Skip confirmation prompts",
2953
- "name": "force",
2968
+ "from-json": {
2969
+ "description": "Compare two results.json files directly (no DB). Pass twice: --from-json PREV --from-json CURR",
2970
+ "name": "from-json",
2971
+ "hasDynamicHelp": false,
2972
+ "multiple": true,
2973
+ "type": "option"
2974
+ },
2975
+ "format": {
2976
+ "char": "f",
2977
+ "description": "Output format",
2978
+ "name": "format",
2979
+ "default": "console",
2980
+ "hasDynamicHelp": false,
2981
+ "multiple": false,
2982
+ "options": [
2983
+ "console",
2984
+ "json",
2985
+ "markdown"
2986
+ ],
2987
+ "type": "option"
2988
+ },
2989
+ "output": {
2990
+ "char": "o",
2991
+ "description": "Output file path",
2992
+ "name": "output",
2993
+ "hasDynamicHelp": false,
2994
+ "multiple": false,
2995
+ "type": "option"
2996
+ },
2997
+ "verbose": {
2998
+ "description": "Show detailed information",
2999
+ "name": "verbose",
2954
3000
  "allowNo": false,
2955
3001
  "type": "boolean"
2956
3002
  },
3003
+ "tag": {
3004
+ "description": "Filter suite runs by tag (matches against MJTestSuiteRunEntity.Tags). Useful for isolating runs from a specific source environment in an archive MJ. DB mode only — --from-json ignores this flag.",
3005
+ "name": "tag",
3006
+ "hasDynamicHelp": false,
3007
+ "multiple": false,
3008
+ "type": "option"
3009
+ }
3010
+ },
3011
+ "hasDynamicHelp": false,
3012
+ "hiddenAliases": [],
3013
+ "id": "test:compare",
3014
+ "pluginAlias": "@memberjunction/cli",
3015
+ "pluginName": "@memberjunction/cli",
3016
+ "pluginType": "core",
3017
+ "strict": true,
3018
+ "enableJsonFlag": false,
3019
+ "isESM": true,
3020
+ "relativePath": [
3021
+ "dist",
3022
+ "commands",
3023
+ "test",
3024
+ "compare.js"
3025
+ ]
3026
+ },
3027
+ "test:history": {
3028
+ "aliases": [],
3029
+ "args": {},
3030
+ "description": "View test execution history",
3031
+ "examples": [
3032
+ "<%= config.bin %> <%= command.id %>",
3033
+ "<%= config.bin %> <%= command.id %> --test=<test-id>",
3034
+ "<%= config.bin %> <%= command.id %> --suite=<suite-id>",
3035
+ "<%= config.bin %> <%= command.id %> --since=\"2024-01-01\"",
3036
+ "<%= config.bin %> <%= command.id %> --limit=50"
3037
+ ],
3038
+ "flags": {
3039
+ "test": {
3040
+ "char": "t",
3041
+ "description": "Filter by test ID",
3042
+ "name": "test",
3043
+ "hasDynamicHelp": false,
3044
+ "multiple": false,
3045
+ "type": "option"
3046
+ },
3047
+ "recent": {
3048
+ "char": "r",
3049
+ "description": "Number of recent runs to show",
3050
+ "name": "recent",
3051
+ "hasDynamicHelp": false,
3052
+ "multiple": false,
3053
+ "type": "option"
3054
+ },
3055
+ "from": {
3056
+ "description": "Show history from date (YYYY-MM-DD)",
3057
+ "name": "from",
3058
+ "hasDynamicHelp": false,
3059
+ "multiple": false,
3060
+ "type": "option"
3061
+ },
3062
+ "status": {
3063
+ "char": "s",
3064
+ "description": "Filter by status",
3065
+ "name": "status",
3066
+ "hasDynamicHelp": false,
3067
+ "multiple": false,
3068
+ "type": "option"
3069
+ },
3070
+ "format": {
3071
+ "char": "f",
3072
+ "description": "Output format",
3073
+ "name": "format",
3074
+ "default": "console",
3075
+ "hasDynamicHelp": false,
3076
+ "multiple": false,
3077
+ "options": [
3078
+ "console",
3079
+ "json",
3080
+ "markdown"
3081
+ ],
3082
+ "type": "option"
3083
+ },
3084
+ "output": {
3085
+ "char": "o",
3086
+ "description": "Output file path",
3087
+ "name": "output",
3088
+ "hasDynamicHelp": false,
3089
+ "multiple": false,
3090
+ "type": "option"
3091
+ },
2957
3092
  "verbose": {
2958
3093
  "char": "v",
2959
- "description": "Show detailed output",
3094
+ "description": "Show detailed information",
2960
3095
  "name": "verbose",
2961
3096
  "allowNo": false,
2962
3097
  "type": "boolean"
@@ -2964,7 +3099,7 @@
2964
3099
  },
2965
3100
  "hasDynamicHelp": false,
2966
3101
  "hiddenAliases": [],
2967
- "id": "sync:file-reset",
3102
+ "id": "test:history",
2968
3103
  "pluginAlias": "@memberjunction/cli",
2969
3104
  "pluginName": "@memberjunction/cli",
2970
3105
  "pluginType": "core",
@@ -2974,21 +3109,26 @@
2974
3109
  "relativePath": [
2975
3110
  "dist",
2976
3111
  "commands",
2977
- "sync",
2978
- "file-reset.js"
3112
+ "test",
3113
+ "history.js"
2979
3114
  ]
2980
3115
  },
2981
- "sync:init": {
3116
+ "test": {
2982
3117
  "aliases": [],
2983
3118
  "args": {},
2984
- "description": "Initialize a directory for metadata synchronization",
3119
+ "description": "MemberJunction Testing Framework - Execute and manage tests",
2985
3120
  "examples": [
2986
- "<%= config.bin %> <%= command.id %>"
3121
+ "<%= config.bin %> <%= command.id %> run <test-id>",
3122
+ "<%= config.bin %> <%= command.id %> run --name=\"Active Members Count\"",
3123
+ "<%= config.bin %> <%= command.id %> suite <suite-id>",
3124
+ "<%= config.bin %> <%= command.id %> list",
3125
+ "<%= config.bin %> <%= command.id %> list --suites",
3126
+ "<%= config.bin %> <%= command.id %> validate --all"
2987
3127
  ],
2988
3128
  "flags": {},
2989
3129
  "hasDynamicHelp": false,
2990
3130
  "hiddenAliases": [],
2991
- "id": "sync:init",
3131
+ "id": "test",
2992
3132
  "pluginAlias": "@memberjunction/cli",
2993
3133
  "pluginName": "@memberjunction/cli",
2994
3134
  "pluginType": "core",
@@ -2998,148 +3138,176 @@
2998
3138
  "relativePath": [
2999
3139
  "dist",
3000
3140
  "commands",
3001
- "sync",
3002
- "init.js"
3141
+ "test",
3142
+ "index.js"
3003
3143
  ]
3004
3144
  },
3005
- "sync:pull": {
3145
+ "test:list": {
3006
3146
  "aliases": [],
3007
3147
  "args": {},
3008
- "description": "Pull metadata from database to local files",
3148
+ "description": "List available tests, suites, and types",
3009
3149
  "examples": [
3010
- "<%= config.bin %> <%= command.id %> --entity=\"MJ: AI Prompts\"",
3011
- "<%= config.bin %> <%= command.id %> --entity=\"MJ: AI Agents\" --merge-strategy=overwrite",
3012
- "<%= config.bin %> <%= command.id %> --entity=\"Templates\" --dry-run --verbose"
3150
+ "<%= config.bin %> <%= command.id %>",
3151
+ "<%= config.bin %> <%= command.id %> --suites",
3152
+ "<%= config.bin %> <%= command.id %> --types",
3153
+ "<%= config.bin %> <%= command.id %> --type=agent-eval",
3154
+ "<%= config.bin %> <%= command.id %> --tag=smoke",
3155
+ "<%= config.bin %> <%= command.id %> --status=active --verbose"
3013
3156
  ],
3014
3157
  "flags": {
3015
- "format": {
3016
- "description": "Output format: text (human), json (machine-readable), md (Markdown-fenced)",
3017
- "name": "format",
3018
- "default": "text",
3019
- "hasDynamicHelp": false,
3020
- "multiple": false,
3021
- "options": [
3022
- "text",
3023
- "json",
3024
- "md"
3025
- ],
3026
- "type": "option"
3027
- },
3028
- "verbose": {
3029
- "char": "v",
3030
- "description": "Show detailed output",
3031
- "name": "verbose",
3158
+ "suites": {
3159
+ "description": "List test suites instead of tests",
3160
+ "name": "suites",
3032
3161
  "allowNo": false,
3033
3162
  "type": "boolean"
3034
3163
  },
3035
- "no-banner": {
3036
- "description": "Suppress the startup banner and runtime advisory",
3037
- "name": "no-banner",
3164
+ "types": {
3165
+ "description": "List test types",
3166
+ "name": "types",
3038
3167
  "allowNo": false,
3039
3168
  "type": "boolean"
3040
3169
  },
3041
- "entity": {
3042
- "description": "Entity name to pull",
3043
- "name": "entity",
3044
- "required": true,
3170
+ "type": {
3171
+ "char": "t",
3172
+ "description": "Filter by test type",
3173
+ "name": "type",
3045
3174
  "hasDynamicHelp": false,
3046
3175
  "multiple": false,
3047
3176
  "type": "option"
3048
3177
  },
3049
- "filter": {
3050
- "description": "Additional filter for pulling specific records",
3051
- "name": "filter",
3178
+ "tag": {
3179
+ "description": "Filter by tag",
3180
+ "name": "tag",
3052
3181
  "hasDynamicHelp": false,
3053
3182
  "multiple": false,
3054
3183
  "type": "option"
3055
3184
  },
3056
- "dry-run": {
3057
- "description": "Show what would be pulled without actually pulling",
3058
- "name": "dry-run",
3059
- "allowNo": false,
3060
- "type": "boolean"
3061
- },
3062
- "multi-file": {
3063
- "description": "Create a single file with multiple records (provide filename)",
3064
- "name": "multi-file",
3185
+ "status": {
3186
+ "char": "s",
3187
+ "description": "Filter by status",
3188
+ "name": "status",
3065
3189
  "hasDynamicHelp": false,
3066
3190
  "multiple": false,
3067
3191
  "type": "option"
3068
3192
  },
3069
- "no-validate": {
3070
- "description": "Skip validation before pull",
3071
- "name": "no-validate",
3072
- "allowNo": false,
3073
- "type": "boolean"
3074
- },
3075
- "update-existing": {
3076
- "description": "Update existing records during pull",
3077
- "name": "update-existing",
3078
- "allowNo": false,
3079
- "type": "boolean"
3080
- },
3081
- "create-new": {
3082
- "description": "Create new files for records not found locally",
3083
- "name": "create-new",
3084
- "allowNo": false,
3085
- "type": "boolean"
3086
- },
3087
- "backup-before-update": {
3088
- "description": "Create backups before updating files",
3089
- "name": "backup-before-update",
3090
- "allowNo": false,
3091
- "type": "boolean"
3092
- },
3093
- "merge-strategy": {
3094
- "description": "Merge strategy for updates",
3095
- "name": "merge-strategy",
3096
- "default": "merge",
3193
+ "format": {
3194
+ "char": "f",
3195
+ "description": "Output format",
3196
+ "name": "format",
3197
+ "default": "console",
3097
3198
  "hasDynamicHelp": false,
3098
3199
  "multiple": false,
3099
3200
  "options": [
3100
- "merge",
3101
- "overwrite",
3102
- "skip"
3201
+ "console",
3202
+ "json",
3203
+ "markdown"
3103
3204
  ],
3104
3205
  "type": "option"
3105
3206
  },
3106
- "backup-directory": {
3107
- "description": "Custom backup directory (default: .backups)",
3108
- "name": "backup-directory",
3207
+ "output": {
3208
+ "char": "o",
3209
+ "description": "Output file path",
3210
+ "name": "output",
3109
3211
  "hasDynamicHelp": false,
3110
3212
  "multiple": false,
3111
3213
  "type": "option"
3112
3214
  },
3113
- "preserve-fields": {
3114
- "description": "Comma-separated list of fields to preserve during updates",
3115
- "name": "preserve-fields",
3215
+ "verbose": {
3216
+ "char": "v",
3217
+ "description": "Show detailed information",
3218
+ "name": "verbose",
3219
+ "allowNo": false,
3220
+ "type": "boolean"
3221
+ }
3222
+ },
3223
+ "hasDynamicHelp": false,
3224
+ "hiddenAliases": [],
3225
+ "id": "test:list",
3226
+ "pluginAlias": "@memberjunction/cli",
3227
+ "pluginName": "@memberjunction/cli",
3228
+ "pluginType": "core",
3229
+ "strict": true,
3230
+ "enableJsonFlag": false,
3231
+ "isESM": true,
3232
+ "relativePath": [
3233
+ "dist",
3234
+ "commands",
3235
+ "test",
3236
+ "list.js"
3237
+ ]
3238
+ },
3239
+ "test:run": {
3240
+ "aliases": [],
3241
+ "args": {
3242
+ "testId": {
3243
+ "description": "Test ID to execute",
3244
+ "name": "testId",
3245
+ "required": false
3246
+ }
3247
+ },
3248
+ "description": "Execute a single test by ID or name",
3249
+ "examples": [
3250
+ "<%= config.bin %> <%= command.id %> <test-id>",
3251
+ "<%= config.bin %> <%= command.id %> --name=\"Active Members Count\"",
3252
+ "<%= config.bin %> <%= command.id %> <test-id> --environment=staging",
3253
+ "<%= config.bin %> <%= command.id %> <test-id> --format=json --output=results.json",
3254
+ "<%= config.bin %> <%= command.id %> <test-id> --dry-run"
3255
+ ],
3256
+ "flags": {
3257
+ "name": {
3258
+ "char": "n",
3259
+ "description": "Test name to execute",
3260
+ "name": "name",
3116
3261
  "hasDynamicHelp": false,
3117
- "multiple": true,
3262
+ "multiple": false,
3118
3263
  "type": "option"
3119
3264
  },
3120
- "exclude-fields": {
3121
- "description": "Comma-separated list of fields to exclude from pull",
3122
- "name": "exclude-fields",
3265
+ "environment": {
3266
+ "char": "e",
3267
+ "description": "Environment context (dev, staging, prod)",
3268
+ "name": "environment",
3123
3269
  "hasDynamicHelp": false,
3124
- "multiple": true,
3270
+ "multiple": false,
3125
3271
  "type": "option"
3126
3272
  },
3127
- "target-dir": {
3128
- "description": "Specific target directory (overrides auto-discovery)",
3129
- "name": "target-dir",
3273
+ "format": {
3274
+ "char": "f",
3275
+ "description": "Output format",
3276
+ "name": "format",
3277
+ "default": "console",
3130
3278
  "hasDynamicHelp": false,
3131
3279
  "multiple": false,
3280
+ "options": [
3281
+ "console",
3282
+ "json",
3283
+ "markdown"
3284
+ ],
3132
3285
  "type": "option"
3133
3286
  },
3134
- "incremental": {
3135
- "description": "Only pull records updated since last successful pull",
3136
- "name": "incremental",
3287
+ "output": {
3288
+ "char": "o",
3289
+ "description": "Output file path",
3290
+ "name": "output",
3291
+ "hasDynamicHelp": false,
3292
+ "multiple": false,
3293
+ "type": "option"
3294
+ },
3295
+ "dry-run": {
3296
+ "description": "Validate without executing",
3297
+ "name": "dry-run",
3137
3298
  "allowNo": false,
3138
3299
  "type": "boolean"
3139
3300
  },
3140
- "since": {
3141
- "description": "Only pull records updated after this ISO 8601 timestamp",
3142
- "name": "since",
3301
+ "verbose": {
3302
+ "char": "v",
3303
+ "description": "Show detailed execution information",
3304
+ "name": "verbose",
3305
+ "allowNo": false,
3306
+ "type": "boolean"
3307
+ },
3308
+ "oracles-module": {
3309
+ "description": "Path to a JS/TS module that exports custom IOracle classes or instances. Each export is registered on the engine before the test runs — used by non-MJ adopters to plug app-specific oracle types without modifying TestingFramework.",
3310
+ "name": "oracles-module",
3143
3311
  "hasDynamicHelp": false,
3144
3312
  "multiple": false,
3145
3313
  "type": "option"
@@ -3147,270 +3315,201 @@
3147
3315
  },
3148
3316
  "hasDynamicHelp": false,
3149
3317
  "hiddenAliases": [],
3150
- "id": "sync:pull",
3318
+ "id": "test:run",
3151
3319
  "pluginAlias": "@memberjunction/cli",
3152
3320
  "pluginName": "@memberjunction/cli",
3153
3321
  "pluginType": "core",
3154
3322
  "strict": true,
3155
3323
  "enableJsonFlag": false,
3156
- "Usage": {
3157
- "domain": "sync",
3158
- "command": "sync:pull",
3159
- "summary": "Pull database records into local metadata files.",
3160
- "description": "Writes records of --entity into the matching entity directory, creating or updating files per the merge strategy.",
3161
- "flags": [
3162
- {
3163
- "name": "--entity",
3164
- "type": "string",
3165
- "description": "Entity name to pull (required)"
3166
- },
3167
- {
3168
- "name": "--filter",
3169
- "type": "string",
3170
- "description": "Extra SQL filter for which records to pull"
3171
- },
3172
- {
3173
- "name": "--merge-strategy",
3174
- "type": "merge|overwrite|skip",
3175
- "description": "How to reconcile existing files"
3176
- },
3177
- {
3178
- "name": "--dry-run",
3179
- "type": "boolean",
3180
- "description": "Report what would be pulled without writing"
3181
- },
3182
- {
3183
- "name": "--format",
3184
- "type": "text|json|md",
3185
- "description": "Output format (json for machine-readable result)"
3186
- }
3187
- ],
3188
- "examples": [
3189
- "mj sync pull --entity=\"MJ: AI Prompts\"",
3190
- "mj sync pull --entity=\"Actions\" --format=json"
3191
- ],
3192
- "runtime": {
3193
- "class": "variable",
3194
- "typicalSeconds": 15,
3195
- "note": "scales with number of records matched for --entity"
3196
- }
3197
- },
3198
3324
  "isESM": true,
3199
3325
  "relativePath": [
3200
3326
  "dist",
3201
3327
  "commands",
3202
- "sync",
3203
- "pull.js"
3328
+ "test",
3329
+ "run.js"
3204
3330
  ]
3205
3331
  },
3206
- "sync:push": {
3332
+ "test:suite": {
3207
3333
  "aliases": [],
3208
- "args": {},
3209
- "description": "Push local file changes to the database",
3334
+ "args": {
3335
+ "suiteId": {
3336
+ "description": "Test suite ID to execute",
3337
+ "name": "suiteId",
3338
+ "required": false
3339
+ }
3340
+ },
3341
+ "description": "Execute a test suite",
3210
3342
  "examples": [
3211
- "<%= config.bin %> <%= command.id %>",
3212
- "<%= config.bin %> <%= command.id %> --dry-run",
3213
- "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
3214
- "<%= config.bin %> <%= command.id %> --ci --format=json"
3343
+ "<%= config.bin %> <%= command.id %> <suite-id>",
3344
+ "<%= config.bin %> <%= command.id %> --name=\"Agent Quality Suite\"",
3345
+ "<%= config.bin %> <%= command.id %> <suite-id> --format=json",
3346
+ "<%= config.bin %> <%= command.id %> <suite-id> --output=suite-results.json"
3215
3347
  ],
3216
3348
  "flags": {
3349
+ "name": {
3350
+ "char": "n",
3351
+ "description": "Test suite name to execute",
3352
+ "name": "name",
3353
+ "hasDynamicHelp": false,
3354
+ "multiple": false,
3355
+ "type": "option"
3356
+ },
3217
3357
  "format": {
3218
- "description": "Output format: text (human), json (machine-readable), md (Markdown-fenced)",
3358
+ "char": "f",
3359
+ "description": "Output format",
3219
3360
  "name": "format",
3220
- "default": "text",
3361
+ "default": "console",
3221
3362
  "hasDynamicHelp": false,
3222
3363
  "multiple": false,
3223
3364
  "options": [
3224
- "text",
3365
+ "console",
3225
3366
  "json",
3226
- "md"
3367
+ "markdown"
3227
3368
  ],
3228
3369
  "type": "option"
3229
3370
  },
3371
+ "output": {
3372
+ "char": "o",
3373
+ "description": "Output file path",
3374
+ "name": "output",
3375
+ "hasDynamicHelp": false,
3376
+ "multiple": false,
3377
+ "type": "option"
3378
+ },
3230
3379
  "verbose": {
3231
3380
  "char": "v",
3232
- "description": "Show detailed output",
3381
+ "description": "Show detailed execution information",
3233
3382
  "name": "verbose",
3234
3383
  "allowNo": false,
3235
3384
  "type": "boolean"
3236
3385
  },
3237
- "no-banner": {
3238
- "description": "Suppress the startup banner and runtime advisory",
3239
- "name": "no-banner",
3240
- "allowNo": false,
3241
- "type": "boolean"
3242
- },
3243
- "dir": {
3244
- "description": "Specific entity directory to push",
3245
- "name": "dir",
3386
+ "delay": {
3387
+ "char": "d",
3388
+ "description": "Delay in milliseconds between test executions (avoids Auth0 rate limits)",
3389
+ "name": "delay",
3390
+ "default": 0,
3246
3391
  "hasDynamicHelp": false,
3247
3392
  "multiple": false,
3248
3393
  "type": "option"
3249
3394
  },
3250
- "dry-run": {
3251
- "description": "Show what would be pushed without actually pushing",
3252
- "name": "dry-run",
3253
- "allowNo": false,
3254
- "type": "boolean"
3255
- },
3256
- "ci": {
3257
- "description": "CI mode - no prompts, fail on issues",
3258
- "name": "ci",
3259
- "allowNo": false,
3260
- "type": "boolean"
3261
- },
3262
- "no-validate": {
3263
- "description": "Skip validation before push",
3264
- "name": "no-validate",
3265
- "allowNo": false,
3266
- "type": "boolean"
3267
- },
3268
- "delete-db-only": {
3269
- "description": "Delete database-only records that reference records being deleted (prevents FK errors)",
3270
- "name": "delete-db-only",
3395
+ "parallel": {
3396
+ "char": "p",
3397
+ "description": "Run tests in parallel with shared browser sessions",
3398
+ "name": "parallel",
3271
3399
  "allowNo": false,
3272
3400
  "type": "boolean"
3273
3401
  },
3274
- "parallel-batch-size": {
3275
- "description": "Number of records to process in parallel (default: 10)",
3276
- "name": "parallel-batch-size",
3277
- "default": 10,
3402
+ "max-parallel": {
3403
+ "description": "Maximum number of parallel workers (default 4)",
3404
+ "name": "max-parallel",
3405
+ "default": 4,
3278
3406
  "hasDynamicHelp": false,
3279
3407
  "multiple": false,
3280
3408
  "type": "option"
3281
3409
  },
3282
- "include": {
3283
- "description": "Only process these directories (comma-separated, supports patterns)",
3284
- "name": "include",
3410
+ "flaky-check": {
3411
+ "description": "Run each test N times to detect flakiness (variance > 0.3 or mixed pass/fail = flaky). Recommended: 3 or 5",
3412
+ "name": "flaky-check",
3285
3413
  "hasDynamicHelp": false,
3286
3414
  "multiple": false,
3287
3415
  "type": "option"
3288
3416
  },
3289
- "exclude": {
3290
- "description": "Skip these directories (comma-separated, supports patterns)",
3291
- "name": "exclude",
3417
+ "oracles-module": {
3418
+ "description": "Path to a JS/TS module that exports custom IOracle classes or instances. Each export is registered on the engine before the suite runs — used by non-MJ adopters to plug app-specific oracle types without modifying TestingFramework.",
3419
+ "name": "oracles-module",
3292
3420
  "hasDynamicHelp": false,
3293
3421
  "multiple": false,
3294
3422
  "type": "option"
3295
- },
3296
- "incremental": {
3297
- "description": "Skip unchanged files using stored checksums from last push",
3298
- "name": "incremental",
3299
- "allowNo": false,
3300
- "type": "boolean"
3301
- },
3302
- "change-detail": {
3303
- "description": "Write a detailed per-record change report (primary keys + field diffs) to a file",
3304
- "name": "change-detail",
3305
- "allowNo": false,
3306
- "type": "boolean"
3307
3423
  }
3308
3424
  },
3309
3425
  "hasDynamicHelp": false,
3310
3426
  "hiddenAliases": [],
3311
- "id": "sync:push",
3427
+ "id": "test:suite",
3312
3428
  "pluginAlias": "@memberjunction/cli",
3313
3429
  "pluginName": "@memberjunction/cli",
3314
3430
  "pluginType": "core",
3315
3431
  "strict": true,
3316
3432
  "enableJsonFlag": false,
3317
- "Usage": {
3318
- "domain": "sync",
3319
- "command": "sync:push",
3320
- "summary": "Push local metadata files to the database (upsert).",
3321
- "description": "Reads entity directories under --dir and creates/updates matching records. Runs validation first unless --no-validate.",
3322
- "flags": [
3323
- {
3324
- "name": "--dir",
3325
- "type": "string",
3326
- "description": "Entity directory to push"
3327
- },
3328
- {
3329
- "name": "--dry-run",
3330
- "type": "boolean",
3331
- "description": "Report what would change without writing"
3332
- },
3333
- {
3334
- "name": "--ci",
3335
- "type": "boolean",
3336
- "description": "No prompts; non-zero exit on error"
3337
- },
3338
- {
3339
- "name": "--no-validate",
3340
- "type": "boolean",
3341
- "description": "Skip pre-push validation"
3342
- },
3343
- {
3344
- "name": "--incremental",
3345
- "type": "boolean",
3346
- "description": "Skip unchanged files using stored checksums"
3347
- },
3348
- {
3349
- "name": "--format",
3350
- "type": "text|json|md",
3351
- "description": "Output format (json for machine-readable result)"
3352
- }
3353
- ],
3354
- "examples": [
3355
- "mj sync push --dir=ai-agents",
3356
- "mj sync push --ci --format=json"
3357
- ],
3358
- "runtime": {
3359
- "class": "variable",
3360
- "typicalSeconds": 20,
3361
- "note": "scales with number of records in --dir"
3362
- }
3363
- },
3364
3433
  "isESM": true,
3365
3434
  "relativePath": [
3366
3435
  "dist",
3367
3436
  "commands",
3368
- "sync",
3369
- "push.js"
3437
+ "test",
3438
+ "suite.js"
3370
3439
  ]
3371
3440
  },
3372
- "sync:status": {
3441
+ "test:validate": {
3373
3442
  "aliases": [],
3374
- "args": {},
3375
- "description": "Show status of local files vs database",
3443
+ "args": {
3444
+ "testId": {
3445
+ "description": "Test ID to validate",
3446
+ "name": "testId",
3447
+ "required": false
3448
+ }
3449
+ },
3450
+ "description": "Validate test definitions without executing",
3376
3451
  "examples": [
3377
- "<%= config.bin %> <%= command.id %>",
3378
- "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
3379
- "<%= config.bin %> <%= command.id %> --verbose"
3452
+ "<%= config.bin %> <%= command.id %> <test-id>",
3453
+ "<%= config.bin %> <%= command.id %> --all",
3454
+ "<%= config.bin %> <%= command.id %> --type=agent-eval",
3455
+ "<%= config.bin %> <%= command.id %> --all --save-report",
3456
+ "<%= config.bin %> <%= command.id %> --all --output=validation-report.md"
3380
3457
  ],
3381
3458
  "flags": {
3382
- "dir": {
3383
- "description": "Specific entity directory to check status",
3384
- "name": "dir",
3459
+ "all": {
3460
+ "char": "a",
3461
+ "description": "Validate all tests",
3462
+ "name": "all",
3463
+ "allowNo": false,
3464
+ "type": "boolean"
3465
+ },
3466
+ "type": {
3467
+ "char": "t",
3468
+ "description": "Validate tests by type",
3469
+ "name": "type",
3385
3470
  "hasDynamicHelp": false,
3386
3471
  "multiple": false,
3387
3472
  "type": "option"
3388
3473
  },
3389
- "verbose": {
3390
- "char": "v",
3391
- "description": "Show detailed field-level differences",
3392
- "name": "verbose",
3474
+ "save-report": {
3475
+ "description": "Save validation report to file",
3476
+ "name": "save-report",
3393
3477
  "allowNo": false,
3394
3478
  "type": "boolean"
3395
3479
  },
3396
- "include": {
3397
- "description": "Only process these directories (comma-separated, supports patterns)",
3398
- "name": "include",
3480
+ "format": {
3481
+ "char": "f",
3482
+ "description": "Output format",
3483
+ "name": "format",
3484
+ "default": "console",
3399
3485
  "hasDynamicHelp": false,
3400
3486
  "multiple": false,
3487
+ "options": [
3488
+ "console",
3489
+ "json",
3490
+ "markdown"
3491
+ ],
3401
3492
  "type": "option"
3402
3493
  },
3403
- "exclude": {
3404
- "description": "Skip these directories (comma-separated, supports patterns)",
3405
- "name": "exclude",
3494
+ "output": {
3495
+ "char": "o",
3496
+ "description": "Output file path",
3497
+ "name": "output",
3406
3498
  "hasDynamicHelp": false,
3407
3499
  "multiple": false,
3408
3500
  "type": "option"
3501
+ },
3502
+ "verbose": {
3503
+ "char": "v",
3504
+ "description": "Show detailed information",
3505
+ "name": "verbose",
3506
+ "allowNo": false,
3507
+ "type": "boolean"
3409
3508
  }
3410
3509
  },
3411
3510
  "hasDynamicHelp": false,
3412
3511
  "hiddenAliases": [],
3413
- "id": "sync:status",
3512
+ "id": "test:validate",
3414
3513
  "pluginAlias": "@memberjunction/cli",
3415
3514
  "pluginName": "@memberjunction/cli",
3416
3515
  "pluginType": "core",
@@ -3420,32 +3519,64 @@
3420
3519
  "relativePath": [
3421
3520
  "dist",
3422
3521
  "commands",
3423
- "sync",
3424
- "status.js"
3522
+ "test",
3523
+ "validate.js"
3425
3524
  ]
3426
3525
  },
3427
- "sync:usage": {
3526
+ "sync:file-reset": {
3428
3527
  "aliases": [],
3429
3528
  "args": {},
3430
- "description": "Show usage, flags, examples, and runtime hints for every `mj sync` command.",
3529
+ "description": "Reset file metadata sections",
3530
+ "examples": [
3531
+ "<%= config.bin %> <%= command.id %>",
3532
+ "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
3533
+ "<%= config.bin %> <%= command.id %> --sections=\"dependencies,references\"",
3534
+ "<%= config.bin %> <%= command.id %> --all"
3535
+ ],
3431
3536
  "flags": {
3432
- "format": {
3433
- "description": "Output format",
3434
- "name": "format",
3435
- "default": "text",
3537
+ "dir": {
3538
+ "description": "Specific entity directory to reset",
3539
+ "name": "dir",
3540
+ "hasDynamicHelp": false,
3541
+ "multiple": false,
3542
+ "type": "option"
3543
+ },
3544
+ "sections": {
3545
+ "description": "Comma-separated list of sections to reset (dependencies,references,related,lookup)",
3546
+ "name": "sections",
3436
3547
  "hasDynamicHelp": false,
3437
3548
  "multiple": false,
3438
- "options": [
3439
- "text",
3440
- "json",
3441
- "md"
3442
- ],
3443
3549
  "type": "option"
3550
+ },
3551
+ "all": {
3552
+ "description": "Reset all metadata sections",
3553
+ "name": "all",
3554
+ "allowNo": false,
3555
+ "type": "boolean"
3556
+ },
3557
+ "dry-run": {
3558
+ "description": "Show what would be reset without actually resetting",
3559
+ "name": "dry-run",
3560
+ "allowNo": false,
3561
+ "type": "boolean"
3562
+ },
3563
+ "force": {
3564
+ "description": "Skip confirmation prompts",
3565
+ "name": "force",
3566
+ "allowNo": false,
3567
+ "type": "boolean"
3568
+ },
3569
+ "verbose": {
3570
+ "char": "v",
3571
+ "description": "Show detailed output",
3572
+ "name": "verbose",
3573
+ "allowNo": false,
3574
+ "type": "boolean"
3444
3575
  }
3445
3576
  },
3446
3577
  "hasDynamicHelp": false,
3447
3578
  "hiddenAliases": [],
3448
- "id": "sync:usage",
3579
+ "id": "sync:file-reset",
3449
3580
  "pluginAlias": "@memberjunction/cli",
3450
3581
  "pluginName": "@memberjunction/cli",
3451
3582
  "pluginType": "core",
@@ -3456,51 +3587,20 @@
3456
3587
  "dist",
3457
3588
  "commands",
3458
3589
  "sync",
3459
- "usage.js"
3590
+ "file-reset.js"
3460
3591
  ]
3461
3592
  },
3462
- "sync:validate": {
3593
+ "sync:init": {
3463
3594
  "aliases": [],
3464
3595
  "args": {},
3465
- "description": "Validate metadata files",
3596
+ "description": "Initialize a directory for metadata synchronization",
3466
3597
  "examples": [
3467
- "<%= config.bin %> <%= command.id %>",
3468
- "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
3469
- "<%= config.bin %> <%= command.id %> --save-report",
3470
- "<%= config.bin %> <%= command.id %> --verbose"
3598
+ "<%= config.bin %> <%= command.id %>"
3471
3599
  ],
3472
- "flags": {
3473
- "dir": {
3474
- "description": "Specific entity directory to validate",
3475
- "name": "dir",
3476
- "hasDynamicHelp": false,
3477
- "multiple": false,
3478
- "type": "option"
3479
- },
3480
- "verbose": {
3481
- "char": "v",
3482
- "description": "Show detailed validation output",
3483
- "name": "verbose",
3484
- "allowNo": false,
3485
- "type": "boolean"
3486
- },
3487
- "save-report": {
3488
- "description": "Save validation report as markdown file",
3489
- "name": "save-report",
3490
- "allowNo": false,
3491
- "type": "boolean"
3492
- },
3493
- "output": {
3494
- "description": "Output file path for validation report (default: validation-report.md)",
3495
- "name": "output",
3496
- "hasDynamicHelp": false,
3497
- "multiple": false,
3498
- "type": "option"
3499
- }
3500
- },
3600
+ "flags": {},
3501
3601
  "hasDynamicHelp": false,
3502
3602
  "hiddenAliases": [],
3503
- "id": "sync:validate",
3603
+ "id": "sync:init",
3504
3604
  "pluginAlias": "@memberjunction/cli",
3505
3605
  "pluginName": "@memberjunction/cli",
3506
3606
  "pluginType": "core",
@@ -3511,156 +3611,147 @@
3511
3611
  "dist",
3512
3612
  "commands",
3513
3613
  "sync",
3514
- "validate.js"
3614
+ "init.js"
3515
3615
  ]
3516
3616
  },
3517
- "sync:watch": {
3617
+ "sync:pull": {
3518
3618
  "aliases": [],
3519
3619
  "args": {},
3520
- "description": "Watch for file changes and sync automatically",
3620
+ "description": "Pull metadata from database to local files",
3521
3621
  "examples": [
3522
- "<%= config.bin %> <%= command.id %>",
3523
- "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
3524
- "<%= config.bin %> <%= command.id %> --debounce=1000",
3525
- "<%= config.bin %> <%= command.id %> --no-validate"
3622
+ "<%= config.bin %> <%= command.id %> --entity=\"MJ: AI Prompts\"",
3623
+ "<%= config.bin %> <%= command.id %> --entity=\"MJ: AI Agents\" --merge-strategy=overwrite",
3624
+ "<%= config.bin %> <%= command.id %> --entity=\"Templates\" --dry-run --verbose"
3526
3625
  ],
3527
3626
  "flags": {
3528
- "dir": {
3529
- "description": "Specific entity directory to watch",
3530
- "name": "dir",
3531
- "hasDynamicHelp": false,
3532
- "multiple": false,
3533
- "type": "option"
3534
- },
3535
- "debounce": {
3536
- "description": "Debounce delay in milliseconds (default: 500)",
3537
- "name": "debounce",
3627
+ "format": {
3628
+ "description": "Output format: text (human), json (machine-readable), md (Markdown-fenced)",
3629
+ "name": "format",
3630
+ "default": "text",
3538
3631
  "hasDynamicHelp": false,
3539
3632
  "multiple": false,
3633
+ "options": [
3634
+ "text",
3635
+ "json",
3636
+ "md"
3637
+ ],
3540
3638
  "type": "option"
3541
3639
  },
3542
- "no-validate": {
3543
- "description": "Skip validation before sync",
3544
- "name": "no-validate",
3545
- "allowNo": false,
3546
- "type": "boolean"
3547
- },
3548
3640
  "verbose": {
3549
3641
  "char": "v",
3550
3642
  "description": "Show detailed output",
3551
3643
  "name": "verbose",
3552
3644
  "allowNo": false,
3553
3645
  "type": "boolean"
3554
- }
3555
- },
3556
- "hasDynamicHelp": false,
3557
- "hiddenAliases": [],
3558
- "id": "sync:watch",
3559
- "pluginAlias": "@memberjunction/cli",
3560
- "pluginName": "@memberjunction/cli",
3561
- "pluginType": "core",
3562
- "strict": true,
3563
- "enableJsonFlag": false,
3564
- "isESM": true,
3565
- "relativePath": [
3566
- "dist",
3567
- "commands",
3568
- "sync",
3569
- "watch.js"
3570
- ]
3571
- },
3572
- "test:compare": {
3573
- "aliases": [],
3574
- "args": {
3575
- "runId1": {
3576
- "description": "First test run ID to compare",
3577
- "name": "runId1",
3578
- "required": false
3579
3646
  },
3580
- "runId2": {
3581
- "description": "Second test run ID to compare",
3582
- "name": "runId2",
3583
- "required": false
3584
- }
3585
- },
3586
- "description": "Compare test runs for regression detection",
3587
- "examples": [
3588
- "<%= config.bin %> <%= command.id %>",
3589
- "<%= config.bin %> <%= command.id %> --latest",
3590
- "<%= config.bin %> <%= command.id %> <run-id-1> <run-id-2>",
3591
- "<%= config.bin %> <%= command.id %> -v 5.17.0 -v 5.18.0",
3592
- "<%= config.bin %> <%= command.id %> -c abc1234 -c def5678",
3593
- "<%= config.bin %> <%= command.id %> --from-json baseline.json latest.json",
3594
- "<%= config.bin %> <%= command.id %> --latest --format=markdown --output=report.md"
3595
- ],
3596
- "flags": {
3597
- "version": {
3598
- "char": "v",
3599
- "description": "Compare runs by version",
3600
- "name": "version",
3647
+ "no-banner": {
3648
+ "description": "Suppress the startup banner and runtime advisory",
3649
+ "name": "no-banner",
3650
+ "allowNo": false,
3651
+ "type": "boolean"
3652
+ },
3653
+ "entity": {
3654
+ "description": "Entity name to pull",
3655
+ "name": "entity",
3656
+ "required": true,
3601
3657
  "hasDynamicHelp": false,
3602
- "multiple": true,
3658
+ "multiple": false,
3603
3659
  "type": "option"
3604
3660
  },
3605
- "commit": {
3606
- "char": "c",
3607
- "description": "Compare runs by git commit",
3608
- "name": "commit",
3661
+ "filter": {
3662
+ "description": "Additional filter for pulling specific records",
3663
+ "name": "filter",
3609
3664
  "hasDynamicHelp": false,
3610
- "multiple": true,
3665
+ "multiple": false,
3611
3666
  "type": "option"
3612
3667
  },
3613
- "diff-only": {
3614
- "description": "Show only differences",
3615
- "name": "diff-only",
3668
+ "dry-run": {
3669
+ "description": "Show what would be pulled without actually pulling",
3670
+ "name": "dry-run",
3616
3671
  "allowNo": false,
3617
3672
  "type": "boolean"
3618
3673
  },
3619
- "latest": {
3620
- "char": "l",
3621
- "description": "Compare the two most recent completed suite runs",
3622
- "name": "latest",
3674
+ "multi-file": {
3675
+ "description": "Create a single file with multiple records (provide filename)",
3676
+ "name": "multi-file",
3677
+ "hasDynamicHelp": false,
3678
+ "multiple": false,
3679
+ "type": "option"
3680
+ },
3681
+ "no-validate": {
3682
+ "description": "Skip validation before pull",
3683
+ "name": "no-validate",
3623
3684
  "allowNo": false,
3624
3685
  "type": "boolean"
3625
3686
  },
3626
- "from-json": {
3627
- "description": "Compare two results.json files directly (no DB). Pass twice: --from-json PREV --from-json CURR",
3628
- "name": "from-json",
3629
- "hasDynamicHelp": false,
3630
- "multiple": true,
3631
- "type": "option"
3687
+ "update-existing": {
3688
+ "description": "Update existing records during pull",
3689
+ "name": "update-existing",
3690
+ "allowNo": false,
3691
+ "type": "boolean"
3632
3692
  },
3633
- "format": {
3634
- "char": "f",
3635
- "description": "Output format",
3636
- "name": "format",
3637
- "default": "console",
3693
+ "create-new": {
3694
+ "description": "Create new files for records not found locally",
3695
+ "name": "create-new",
3696
+ "allowNo": false,
3697
+ "type": "boolean"
3698
+ },
3699
+ "backup-before-update": {
3700
+ "description": "Create backups before updating files",
3701
+ "name": "backup-before-update",
3702
+ "allowNo": false,
3703
+ "type": "boolean"
3704
+ },
3705
+ "merge-strategy": {
3706
+ "description": "Merge strategy for updates",
3707
+ "name": "merge-strategy",
3708
+ "default": "merge",
3638
3709
  "hasDynamicHelp": false,
3639
3710
  "multiple": false,
3640
3711
  "options": [
3641
- "console",
3642
- "json",
3643
- "markdown"
3712
+ "merge",
3713
+ "overwrite",
3714
+ "skip"
3644
3715
  ],
3645
3716
  "type": "option"
3646
3717
  },
3647
- "output": {
3648
- "char": "o",
3649
- "description": "Output file path",
3650
- "name": "output",
3718
+ "backup-directory": {
3719
+ "description": "Custom backup directory (default: .backups)",
3720
+ "name": "backup-directory",
3651
3721
  "hasDynamicHelp": false,
3652
3722
  "multiple": false,
3653
3723
  "type": "option"
3654
3724
  },
3655
- "verbose": {
3656
- "description": "Show detailed information",
3657
- "name": "verbose",
3725
+ "preserve-fields": {
3726
+ "description": "Comma-separated list of fields to preserve during updates",
3727
+ "name": "preserve-fields",
3728
+ "hasDynamicHelp": false,
3729
+ "multiple": true,
3730
+ "type": "option"
3731
+ },
3732
+ "exclude-fields": {
3733
+ "description": "Comma-separated list of fields to exclude from pull",
3734
+ "name": "exclude-fields",
3735
+ "hasDynamicHelp": false,
3736
+ "multiple": true,
3737
+ "type": "option"
3738
+ },
3739
+ "target-dir": {
3740
+ "description": "Specific target directory (overrides auto-discovery)",
3741
+ "name": "target-dir",
3742
+ "hasDynamicHelp": false,
3743
+ "multiple": false,
3744
+ "type": "option"
3745
+ },
3746
+ "incremental": {
3747
+ "description": "Only pull records updated since last successful pull",
3748
+ "name": "incremental",
3658
3749
  "allowNo": false,
3659
3750
  "type": "boolean"
3660
3751
  },
3661
- "tag": {
3662
- "description": "Filter suite runs by tag (matches against MJTestSuiteRunEntity.Tags). Useful for isolating runs from a specific source environment in an archive MJ. DB mode only — --from-json ignores this flag.",
3663
- "name": "tag",
3752
+ "since": {
3753
+ "description": "Only pull records updated after this ISO 8601 timestamp",
3754
+ "name": "since",
3664
3755
  "hasDynamicHelp": false,
3665
3756
  "multiple": false,
3666
3757
  "type": "option"
@@ -3668,219 +3759,270 @@
3668
3759
  },
3669
3760
  "hasDynamicHelp": false,
3670
3761
  "hiddenAliases": [],
3671
- "id": "test:compare",
3762
+ "id": "sync:pull",
3672
3763
  "pluginAlias": "@memberjunction/cli",
3673
3764
  "pluginName": "@memberjunction/cli",
3674
3765
  "pluginType": "core",
3675
3766
  "strict": true,
3676
3767
  "enableJsonFlag": false,
3677
- "isESM": true,
3678
- "relativePath": [
3679
- "dist",
3680
- "commands",
3681
- "test",
3682
- "compare.js"
3683
- ]
3684
- },
3685
- "test:history": {
3768
+ "Usage": {
3769
+ "domain": "sync",
3770
+ "command": "sync:pull",
3771
+ "summary": "Pull database records into local metadata files.",
3772
+ "description": "Writes records of --entity into the matching entity directory, creating or updating files per the merge strategy.",
3773
+ "flags": [
3774
+ {
3775
+ "name": "--entity",
3776
+ "type": "string",
3777
+ "description": "Entity name to pull (required)"
3778
+ },
3779
+ {
3780
+ "name": "--filter",
3781
+ "type": "string",
3782
+ "description": "Extra SQL filter for which records to pull"
3783
+ },
3784
+ {
3785
+ "name": "--merge-strategy",
3786
+ "type": "merge|overwrite|skip",
3787
+ "description": "How to reconcile existing files"
3788
+ },
3789
+ {
3790
+ "name": "--dry-run",
3791
+ "type": "boolean",
3792
+ "description": "Report what would be pulled without writing"
3793
+ },
3794
+ {
3795
+ "name": "--format",
3796
+ "type": "text|json|md",
3797
+ "description": "Output format (json for machine-readable result)"
3798
+ }
3799
+ ],
3800
+ "examples": [
3801
+ "mj sync pull --entity=\"MJ: AI Prompts\"",
3802
+ "mj sync pull --entity=\"Actions\" --format=json"
3803
+ ],
3804
+ "runtime": {
3805
+ "class": "variable",
3806
+ "typicalSeconds": 15,
3807
+ "note": "scales with number of records matched for --entity"
3808
+ }
3809
+ },
3810
+ "isESM": true,
3811
+ "relativePath": [
3812
+ "dist",
3813
+ "commands",
3814
+ "sync",
3815
+ "pull.js"
3816
+ ]
3817
+ },
3818
+ "sync:push": {
3686
3819
  "aliases": [],
3687
3820
  "args": {},
3688
- "description": "View test execution history",
3821
+ "description": "Push local file changes to the database",
3689
3822
  "examples": [
3690
3823
  "<%= config.bin %> <%= command.id %>",
3691
- "<%= config.bin %> <%= command.id %> --test=<test-id>",
3692
- "<%= config.bin %> <%= command.id %> --suite=<suite-id>",
3693
- "<%= config.bin %> <%= command.id %> --since=\"2024-01-01\"",
3694
- "<%= config.bin %> <%= command.id %> --limit=50"
3824
+ "<%= config.bin %> <%= command.id %> --dry-run",
3825
+ "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
3826
+ "<%= config.bin %> <%= command.id %> --ci --format=json"
3695
3827
  ],
3696
3828
  "flags": {
3697
- "test": {
3698
- "char": "t",
3699
- "description": "Filter by test ID",
3700
- "name": "test",
3829
+ "format": {
3830
+ "description": "Output format: text (human), json (machine-readable), md (Markdown-fenced)",
3831
+ "name": "format",
3832
+ "default": "text",
3701
3833
  "hasDynamicHelp": false,
3702
3834
  "multiple": false,
3835
+ "options": [
3836
+ "text",
3837
+ "json",
3838
+ "md"
3839
+ ],
3703
3840
  "type": "option"
3704
3841
  },
3705
- "recent": {
3706
- "char": "r",
3707
- "description": "Number of recent runs to show",
3708
- "name": "recent",
3709
- "hasDynamicHelp": false,
3710
- "multiple": false,
3711
- "type": "option"
3842
+ "verbose": {
3843
+ "char": "v",
3844
+ "description": "Show detailed output",
3845
+ "name": "verbose",
3846
+ "allowNo": false,
3847
+ "type": "boolean"
3712
3848
  },
3713
- "from": {
3714
- "description": "Show history from date (YYYY-MM-DD)",
3715
- "name": "from",
3849
+ "no-banner": {
3850
+ "description": "Suppress the startup banner and runtime advisory",
3851
+ "name": "no-banner",
3852
+ "allowNo": false,
3853
+ "type": "boolean"
3854
+ },
3855
+ "dir": {
3856
+ "description": "Specific entity directory to push",
3857
+ "name": "dir",
3716
3858
  "hasDynamicHelp": false,
3717
3859
  "multiple": false,
3718
3860
  "type": "option"
3719
3861
  },
3720
- "status": {
3721
- "char": "s",
3722
- "description": "Filter by status",
3723
- "name": "status",
3862
+ "dry-run": {
3863
+ "description": "Show what would be pushed without actually pushing",
3864
+ "name": "dry-run",
3865
+ "allowNo": false,
3866
+ "type": "boolean"
3867
+ },
3868
+ "ci": {
3869
+ "description": "CI mode - no prompts, fail on issues",
3870
+ "name": "ci",
3871
+ "allowNo": false,
3872
+ "type": "boolean"
3873
+ },
3874
+ "no-validate": {
3875
+ "description": "Skip validation before push",
3876
+ "name": "no-validate",
3877
+ "allowNo": false,
3878
+ "type": "boolean"
3879
+ },
3880
+ "delete-db-only": {
3881
+ "description": "Delete database-only records that reference records being deleted (prevents FK errors)",
3882
+ "name": "delete-db-only",
3883
+ "allowNo": false,
3884
+ "type": "boolean"
3885
+ },
3886
+ "parallel-batch-size": {
3887
+ "description": "Number of records to process in parallel (default: 10)",
3888
+ "name": "parallel-batch-size",
3889
+ "default": 10,
3724
3890
  "hasDynamicHelp": false,
3725
3891
  "multiple": false,
3726
3892
  "type": "option"
3727
3893
  },
3728
- "format": {
3729
- "char": "f",
3730
- "description": "Output format",
3731
- "name": "format",
3732
- "default": "console",
3894
+ "include": {
3895
+ "description": "Only process these directories (comma-separated, supports patterns)",
3896
+ "name": "include",
3733
3897
  "hasDynamicHelp": false,
3734
3898
  "multiple": false,
3735
- "options": [
3736
- "console",
3737
- "json",
3738
- "markdown"
3739
- ],
3740
3899
  "type": "option"
3741
3900
  },
3742
- "output": {
3743
- "char": "o",
3744
- "description": "Output file path",
3745
- "name": "output",
3901
+ "exclude": {
3902
+ "description": "Skip these directories (comma-separated, supports patterns)",
3903
+ "name": "exclude",
3746
3904
  "hasDynamicHelp": false,
3747
3905
  "multiple": false,
3748
3906
  "type": "option"
3749
3907
  },
3750
- "verbose": {
3751
- "char": "v",
3752
- "description": "Show detailed information",
3753
- "name": "verbose",
3908
+ "incremental": {
3909
+ "description": "Skip unchanged files using stored checksums from last push",
3910
+ "name": "incremental",
3911
+ "allowNo": false,
3912
+ "type": "boolean"
3913
+ },
3914
+ "change-detail": {
3915
+ "description": "Write a detailed per-record change report (primary keys + field diffs) to a file",
3916
+ "name": "change-detail",
3754
3917
  "allowNo": false,
3755
3918
  "type": "boolean"
3756
3919
  }
3757
3920
  },
3758
3921
  "hasDynamicHelp": false,
3759
3922
  "hiddenAliases": [],
3760
- "id": "test:history",
3761
- "pluginAlias": "@memberjunction/cli",
3762
- "pluginName": "@memberjunction/cli",
3763
- "pluginType": "core",
3764
- "strict": true,
3765
- "enableJsonFlag": false,
3766
- "isESM": true,
3767
- "relativePath": [
3768
- "dist",
3769
- "commands",
3770
- "test",
3771
- "history.js"
3772
- ]
3773
- },
3774
- "test": {
3775
- "aliases": [],
3776
- "args": {},
3777
- "description": "MemberJunction Testing Framework - Execute and manage tests",
3778
- "examples": [
3779
- "<%= config.bin %> <%= command.id %> run <test-id>",
3780
- "<%= config.bin %> <%= command.id %> run --name=\"Active Members Count\"",
3781
- "<%= config.bin %> <%= command.id %> suite <suite-id>",
3782
- "<%= config.bin %> <%= command.id %> list",
3783
- "<%= config.bin %> <%= command.id %> list --suites",
3784
- "<%= config.bin %> <%= command.id %> validate --all"
3785
- ],
3786
- "flags": {},
3787
- "hasDynamicHelp": false,
3788
- "hiddenAliases": [],
3789
- "id": "test",
3923
+ "id": "sync:push",
3790
3924
  "pluginAlias": "@memberjunction/cli",
3791
3925
  "pluginName": "@memberjunction/cli",
3792
3926
  "pluginType": "core",
3793
3927
  "strict": true,
3794
3928
  "enableJsonFlag": false,
3929
+ "Usage": {
3930
+ "domain": "sync",
3931
+ "command": "sync:push",
3932
+ "summary": "Push local metadata files to the database (upsert).",
3933
+ "description": "Reads entity directories under --dir and creates/updates matching records. Runs validation first unless --no-validate.",
3934
+ "flags": [
3935
+ {
3936
+ "name": "--dir",
3937
+ "type": "string",
3938
+ "description": "Entity directory to push"
3939
+ },
3940
+ {
3941
+ "name": "--dry-run",
3942
+ "type": "boolean",
3943
+ "description": "Report what would change without writing"
3944
+ },
3945
+ {
3946
+ "name": "--ci",
3947
+ "type": "boolean",
3948
+ "description": "No prompts; non-zero exit on error"
3949
+ },
3950
+ {
3951
+ "name": "--no-validate",
3952
+ "type": "boolean",
3953
+ "description": "Skip pre-push validation"
3954
+ },
3955
+ {
3956
+ "name": "--incremental",
3957
+ "type": "boolean",
3958
+ "description": "Skip unchanged files using stored checksums"
3959
+ },
3960
+ {
3961
+ "name": "--format",
3962
+ "type": "text|json|md",
3963
+ "description": "Output format (json for machine-readable result)"
3964
+ }
3965
+ ],
3966
+ "examples": [
3967
+ "mj sync push --dir=ai-agents",
3968
+ "mj sync push --ci --format=json"
3969
+ ],
3970
+ "runtime": {
3971
+ "class": "variable",
3972
+ "typicalSeconds": 20,
3973
+ "note": "scales with number of records in --dir"
3974
+ }
3975
+ },
3795
3976
  "isESM": true,
3796
3977
  "relativePath": [
3797
3978
  "dist",
3798
3979
  "commands",
3799
- "test",
3800
- "index.js"
3980
+ "sync",
3981
+ "push.js"
3801
3982
  ]
3802
3983
  },
3803
- "test:list": {
3984
+ "sync:status": {
3804
3985
  "aliases": [],
3805
3986
  "args": {},
3806
- "description": "List available tests, suites, and types",
3987
+ "description": "Show status of local files vs database",
3807
3988
  "examples": [
3808
3989
  "<%= config.bin %> <%= command.id %>",
3809
- "<%= config.bin %> <%= command.id %> --suites",
3810
- "<%= config.bin %> <%= command.id %> --types",
3811
- "<%= config.bin %> <%= command.id %> --type=agent-eval",
3812
- "<%= config.bin %> <%= command.id %> --tag=smoke",
3813
- "<%= config.bin %> <%= command.id %> --status=active --verbose"
3990
+ "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
3991
+ "<%= config.bin %> <%= command.id %> --verbose"
3814
3992
  ],
3815
3993
  "flags": {
3816
- "suites": {
3817
- "description": "List test suites instead of tests",
3818
- "name": "suites",
3819
- "allowNo": false,
3820
- "type": "boolean"
3821
- },
3822
- "types": {
3823
- "description": "List test types",
3824
- "name": "types",
3825
- "allowNo": false,
3826
- "type": "boolean"
3827
- },
3828
- "type": {
3829
- "char": "t",
3830
- "description": "Filter by test type",
3831
- "name": "type",
3832
- "hasDynamicHelp": false,
3833
- "multiple": false,
3834
- "type": "option"
3835
- },
3836
- "tag": {
3837
- "description": "Filter by tag",
3838
- "name": "tag",
3839
- "hasDynamicHelp": false,
3840
- "multiple": false,
3841
- "type": "option"
3842
- },
3843
- "status": {
3844
- "char": "s",
3845
- "description": "Filter by status",
3846
- "name": "status",
3847
- "hasDynamicHelp": false,
3848
- "multiple": false,
3849
- "type": "option"
3850
- },
3851
- "format": {
3852
- "char": "f",
3853
- "description": "Output format",
3854
- "name": "format",
3855
- "default": "console",
3856
- "hasDynamicHelp": false,
3857
- "multiple": false,
3858
- "options": [
3859
- "console",
3860
- "json",
3861
- "markdown"
3862
- ],
3863
- "type": "option"
3864
- },
3865
- "output": {
3866
- "char": "o",
3867
- "description": "Output file path",
3868
- "name": "output",
3994
+ "dir": {
3995
+ "description": "Specific entity directory to check status",
3996
+ "name": "dir",
3869
3997
  "hasDynamicHelp": false,
3870
3998
  "multiple": false,
3871
3999
  "type": "option"
3872
4000
  },
3873
4001
  "verbose": {
3874
4002
  "char": "v",
3875
- "description": "Show detailed information",
4003
+ "description": "Show detailed field-level differences",
3876
4004
  "name": "verbose",
3877
4005
  "allowNo": false,
3878
4006
  "type": "boolean"
4007
+ },
4008
+ "include": {
4009
+ "description": "Only process these directories (comma-separated, supports patterns)",
4010
+ "name": "include",
4011
+ "hasDynamicHelp": false,
4012
+ "multiple": false,
4013
+ "type": "option"
4014
+ },
4015
+ "exclude": {
4016
+ "description": "Skip these directories (comma-separated, supports patterns)",
4017
+ "name": "exclude",
4018
+ "hasDynamicHelp": false,
4019
+ "multiple": false,
4020
+ "type": "option"
3879
4021
  }
3880
4022
  },
3881
4023
  "hasDynamicHelp": false,
3882
4024
  "hiddenAliases": [],
3883
- "id": "test:list",
4025
+ "id": "sync:status",
3884
4026
  "pluginAlias": "@memberjunction/cli",
3885
4027
  "pluginName": "@memberjunction/cli",
3886
4028
  "pluginType": "core",
@@ -3890,90 +4032,32 @@
3890
4032
  "relativePath": [
3891
4033
  "dist",
3892
4034
  "commands",
3893
- "test",
3894
- "list.js"
4035
+ "sync",
4036
+ "status.js"
3895
4037
  ]
3896
4038
  },
3897
- "test:run": {
4039
+ "sync:usage": {
3898
4040
  "aliases": [],
3899
- "args": {
3900
- "testId": {
3901
- "description": "Test ID to execute",
3902
- "name": "testId",
3903
- "required": false
3904
- }
3905
- },
3906
- "description": "Execute a single test by ID or name",
3907
- "examples": [
3908
- "<%= config.bin %> <%= command.id %> <test-id>",
3909
- "<%= config.bin %> <%= command.id %> --name=\"Active Members Count\"",
3910
- "<%= config.bin %> <%= command.id %> <test-id> --environment=staging",
3911
- "<%= config.bin %> <%= command.id %> <test-id> --format=json --output=results.json",
3912
- "<%= config.bin %> <%= command.id %> <test-id> --dry-run"
3913
- ],
4041
+ "args": {},
4042
+ "description": "Show usage, flags, examples, and runtime hints for every `mj sync` command.",
3914
4043
  "flags": {
3915
- "name": {
3916
- "char": "n",
3917
- "description": "Test name to execute",
3918
- "name": "name",
3919
- "hasDynamicHelp": false,
3920
- "multiple": false,
3921
- "type": "option"
3922
- },
3923
- "environment": {
3924
- "char": "e",
3925
- "description": "Environment context (dev, staging, prod)",
3926
- "name": "environment",
3927
- "hasDynamicHelp": false,
3928
- "multiple": false,
3929
- "type": "option"
3930
- },
3931
4044
  "format": {
3932
- "char": "f",
3933
4045
  "description": "Output format",
3934
4046
  "name": "format",
3935
- "default": "console",
4047
+ "default": "text",
3936
4048
  "hasDynamicHelp": false,
3937
4049
  "multiple": false,
3938
4050
  "options": [
3939
- "console",
4051
+ "text",
3940
4052
  "json",
3941
- "markdown"
4053
+ "md"
3942
4054
  ],
3943
4055
  "type": "option"
3944
- },
3945
- "output": {
3946
- "char": "o",
3947
- "description": "Output file path",
3948
- "name": "output",
3949
- "hasDynamicHelp": false,
3950
- "multiple": false,
3951
- "type": "option"
3952
- },
3953
- "dry-run": {
3954
- "description": "Validate without executing",
3955
- "name": "dry-run",
3956
- "allowNo": false,
3957
- "type": "boolean"
3958
- },
3959
- "verbose": {
3960
- "char": "v",
3961
- "description": "Show detailed execution information",
3962
- "name": "verbose",
3963
- "allowNo": false,
3964
- "type": "boolean"
3965
- },
3966
- "oracles-module": {
3967
- "description": "Path to a JS/TS module that exports custom IOracle classes or instances. Each export is registered on the engine before the test runs — used by non-MJ adopters to plug app-specific oracle types without modifying TestingFramework.",
3968
- "name": "oracles-module",
3969
- "hasDynamicHelp": false,
3970
- "multiple": false,
3971
- "type": "option"
3972
4056
  }
3973
4057
  },
3974
4058
  "hasDynamicHelp": false,
3975
4059
  "hiddenAliases": [],
3976
- "id": "test:run",
4060
+ "id": "sync:usage",
3977
4061
  "pluginAlias": "@memberjunction/cli",
3978
4062
  "pluginName": "@memberjunction/cli",
3979
4063
  "pluginType": "core",
@@ -3983,98 +4067,44 @@
3983
4067
  "relativePath": [
3984
4068
  "dist",
3985
4069
  "commands",
3986
- "test",
3987
- "run.js"
4070
+ "sync",
4071
+ "usage.js"
3988
4072
  ]
3989
4073
  },
3990
- "test:suite": {
4074
+ "sync:validate": {
3991
4075
  "aliases": [],
3992
- "args": {
3993
- "suiteId": {
3994
- "description": "Test suite ID to execute",
3995
- "name": "suiteId",
3996
- "required": false
3997
- }
3998
- },
3999
- "description": "Execute a test suite",
4076
+ "args": {},
4077
+ "description": "Validate metadata files",
4000
4078
  "examples": [
4001
- "<%= config.bin %> <%= command.id %> <suite-id>",
4002
- "<%= config.bin %> <%= command.id %> --name=\"Agent Quality Suite\"",
4003
- "<%= config.bin %> <%= command.id %> <suite-id> --format=json",
4004
- "<%= config.bin %> <%= command.id %> <suite-id> --output=suite-results.json"
4079
+ "<%= config.bin %> <%= command.id %>",
4080
+ "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
4081
+ "<%= config.bin %> <%= command.id %> --save-report",
4082
+ "<%= config.bin %> <%= command.id %> --verbose"
4005
4083
  ],
4006
4084
  "flags": {
4007
- "name": {
4008
- "char": "n",
4009
- "description": "Test suite name to execute",
4010
- "name": "name",
4011
- "hasDynamicHelp": false,
4012
- "multiple": false,
4013
- "type": "option"
4014
- },
4015
- "format": {
4016
- "char": "f",
4017
- "description": "Output format",
4018
- "name": "format",
4019
- "default": "console",
4020
- "hasDynamicHelp": false,
4021
- "multiple": false,
4022
- "options": [
4023
- "console",
4024
- "json",
4025
- "markdown"
4026
- ],
4027
- "type": "option"
4028
- },
4029
- "output": {
4030
- "char": "o",
4031
- "description": "Output file path",
4032
- "name": "output",
4085
+ "dir": {
4086
+ "description": "Specific entity directory to validate",
4087
+ "name": "dir",
4033
4088
  "hasDynamicHelp": false,
4034
4089
  "multiple": false,
4035
4090
  "type": "option"
4036
4091
  },
4037
4092
  "verbose": {
4038
4093
  "char": "v",
4039
- "description": "Show detailed execution information",
4094
+ "description": "Show detailed validation output",
4040
4095
  "name": "verbose",
4041
4096
  "allowNo": false,
4042
4097
  "type": "boolean"
4043
4098
  },
4044
- "delay": {
4045
- "char": "d",
4046
- "description": "Delay in milliseconds between test executions (avoids Auth0 rate limits)",
4047
- "name": "delay",
4048
- "default": 0,
4049
- "hasDynamicHelp": false,
4050
- "multiple": false,
4051
- "type": "option"
4052
- },
4053
- "parallel": {
4054
- "char": "p",
4055
- "description": "Run tests in parallel with shared browser sessions",
4056
- "name": "parallel",
4099
+ "save-report": {
4100
+ "description": "Save validation report as markdown file",
4101
+ "name": "save-report",
4057
4102
  "allowNo": false,
4058
4103
  "type": "boolean"
4059
4104
  },
4060
- "max-parallel": {
4061
- "description": "Maximum number of parallel workers (default 4)",
4062
- "name": "max-parallel",
4063
- "default": 4,
4064
- "hasDynamicHelp": false,
4065
- "multiple": false,
4066
- "type": "option"
4067
- },
4068
- "flaky-check": {
4069
- "description": "Run each test N times to detect flakiness (variance > 0.3 or mixed pass/fail = flaky). Recommended: 3 or 5",
4070
- "name": "flaky-check",
4071
- "hasDynamicHelp": false,
4072
- "multiple": false,
4073
- "type": "option"
4074
- },
4075
- "oracles-module": {
4076
- "description": "Path to a JS/TS module that exports custom IOracle classes or instances. Each export is registered on the engine before the suite runs — used by non-MJ adopters to plug app-specific oracle types without modifying TestingFramework.",
4077
- "name": "oracles-module",
4105
+ "output": {
4106
+ "description": "Output file path for validation report (default: validation-report.md)",
4107
+ "name": "output",
4078
4108
  "hasDynamicHelp": false,
4079
4109
  "multiple": false,
4080
4110
  "type": "option"
@@ -4082,7 +4112,7 @@
4082
4112
  },
4083
4113
  "hasDynamicHelp": false,
4084
4114
  "hiddenAliases": [],
4085
- "id": "test:suite",
4115
+ "id": "sync:validate",
4086
4116
  "pluginAlias": "@memberjunction/cli",
4087
4117
  "pluginName": "@memberjunction/cli",
4088
4118
  "pluginType": "core",
@@ -4092,74 +4122,44 @@
4092
4122
  "relativePath": [
4093
4123
  "dist",
4094
4124
  "commands",
4095
- "test",
4096
- "suite.js"
4125
+ "sync",
4126
+ "validate.js"
4097
4127
  ]
4098
4128
  },
4099
- "test:validate": {
4129
+ "sync:watch": {
4100
4130
  "aliases": [],
4101
- "args": {
4102
- "testId": {
4103
- "description": "Test ID to validate",
4104
- "name": "testId",
4105
- "required": false
4106
- }
4107
- },
4108
- "description": "Validate test definitions without executing",
4131
+ "args": {},
4132
+ "description": "Watch for file changes and sync automatically",
4109
4133
  "examples": [
4110
- "<%= config.bin %> <%= command.id %> <test-id>",
4111
- "<%= config.bin %> <%= command.id %> --all",
4112
- "<%= config.bin %> <%= command.id %> --type=agent-eval",
4113
- "<%= config.bin %> <%= command.id %> --all --save-report",
4114
- "<%= config.bin %> <%= command.id %> --all --output=validation-report.md"
4134
+ "<%= config.bin %> <%= command.id %>",
4135
+ "<%= config.bin %> <%= command.id %> --dir=\"ai-prompts\"",
4136
+ "<%= config.bin %> <%= command.id %> --debounce=1000",
4137
+ "<%= config.bin %> <%= command.id %> --no-validate"
4115
4138
  ],
4116
4139
  "flags": {
4117
- "all": {
4118
- "char": "a",
4119
- "description": "Validate all tests",
4120
- "name": "all",
4121
- "allowNo": false,
4122
- "type": "boolean"
4123
- },
4124
- "type": {
4125
- "char": "t",
4126
- "description": "Validate tests by type",
4127
- "name": "type",
4140
+ "dir": {
4141
+ "description": "Specific entity directory to watch",
4142
+ "name": "dir",
4128
4143
  "hasDynamicHelp": false,
4129
4144
  "multiple": false,
4130
4145
  "type": "option"
4131
4146
  },
4132
- "save-report": {
4133
- "description": "Save validation report to file",
4134
- "name": "save-report",
4135
- "allowNo": false,
4136
- "type": "boolean"
4137
- },
4138
- "format": {
4139
- "char": "f",
4140
- "description": "Output format",
4141
- "name": "format",
4142
- "default": "console",
4147
+ "debounce": {
4148
+ "description": "Debounce delay in milliseconds (default: 500)",
4149
+ "name": "debounce",
4143
4150
  "hasDynamicHelp": false,
4144
4151
  "multiple": false,
4145
- "options": [
4146
- "console",
4147
- "json",
4148
- "markdown"
4149
- ],
4150
4152
  "type": "option"
4151
4153
  },
4152
- "output": {
4153
- "char": "o",
4154
- "description": "Output file path",
4155
- "name": "output",
4156
- "hasDynamicHelp": false,
4157
- "multiple": false,
4158
- "type": "option"
4154
+ "no-validate": {
4155
+ "description": "Skip validation before sync",
4156
+ "name": "no-validate",
4157
+ "allowNo": false,
4158
+ "type": "boolean"
4159
4159
  },
4160
4160
  "verbose": {
4161
4161
  "char": "v",
4162
- "description": "Show detailed information",
4162
+ "description": "Show detailed output",
4163
4163
  "name": "verbose",
4164
4164
  "allowNo": false,
4165
4165
  "type": "boolean"
@@ -4167,7 +4167,7 @@
4167
4167
  },
4168
4168
  "hasDynamicHelp": false,
4169
4169
  "hiddenAliases": [],
4170
- "id": "test:validate",
4170
+ "id": "sync:watch",
4171
4171
  "pluginAlias": "@memberjunction/cli",
4172
4172
  "pluginName": "@memberjunction/cli",
4173
4173
  "pluginType": "core",
@@ -4177,8 +4177,8 @@
4177
4177
  "relativePath": [
4178
4178
  "dist",
4179
4179
  "commands",
4180
- "test",
4181
- "validate.js"
4180
+ "sync",
4181
+ "watch.js"
4182
4182
  ]
4183
4183
  },
4184
4184
  "translate-sql": {
@@ -5466,5 +5466,5 @@
5466
5466
  ]
5467
5467
  }
5468
5468
  },
5469
- "version": "5.47.0"
5469
+ "version": "5.48.0"
5470
5470
  }