@neverinfamous/postgres-mcp 2.0.0 → 2.1.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.
- package/LICENSE +1 -1
- package/README.md +76 -9
- package/dist/__tests__/benchmarks/schema-parsing.bench.js +1 -1
- package/dist/__tests__/benchmarks/schema-parsing.bench.js.map +1 -1
- package/dist/__tests__/mocks/adapter.d.ts.map +1 -1
- package/dist/__tests__/mocks/adapter.js +2 -1
- package/dist/__tests__/mocks/adapter.js.map +1 -1
- package/dist/adapters/DatabaseAdapter.d.ts +6 -1
- package/dist/adapters/DatabaseAdapter.d.ts.map +1 -1
- package/dist/adapters/DatabaseAdapter.js +11 -7
- package/dist/adapters/DatabaseAdapter.js.map +1 -1
- package/dist/adapters/postgresql/PostgresAdapter.d.ts +5 -22
- package/dist/adapters/postgresql/PostgresAdapter.d.ts.map +1 -1
- package/dist/adapters/postgresql/PostgresAdapter.js +28 -520
- package/dist/adapters/postgresql/PostgresAdapter.js.map +1 -1
- package/dist/adapters/postgresql/prompts/index.js +1 -1
- package/dist/adapters/postgresql/prompts/index.js.map +1 -1
- package/dist/adapters/postgresql/resources/index.d.ts +1 -1
- package/dist/adapters/postgresql/resources/index.js +3 -3
- package/dist/adapters/postgresql/resources/index.js.map +1 -1
- package/dist/adapters/postgresql/schema-operations.d.ts +71 -0
- package/dist/adapters/postgresql/schema-operations.d.ts.map +1 -0
- package/dist/adapters/postgresql/schema-operations.js +561 -0
- package/dist/adapters/postgresql/schema-operations.js.map +1 -0
- package/dist/adapters/postgresql/schemas/admin.d.ts +4 -4
- package/dist/adapters/postgresql/schemas/admin.js +4 -4
- package/dist/adapters/postgresql/schemas/admin.js.map +1 -1
- package/dist/adapters/postgresql/schemas/backup.d.ts +2 -2
- package/dist/adapters/postgresql/schemas/backup.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/backup.js +1 -3
- package/dist/adapters/postgresql/schemas/backup.js.map +1 -1
- package/dist/adapters/postgresql/schemas/core/index.d.ts +6 -0
- package/dist/adapters/postgresql/schemas/core/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/core/index.js +6 -0
- package/dist/adapters/postgresql/schemas/core/index.js.map +1 -0
- package/dist/adapters/postgresql/schemas/{core.d.ts → core/queries.d.ts} +12 -167
- package/dist/adapters/postgresql/schemas/core/queries.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/{core.js → core/queries.js} +5 -213
- package/dist/adapters/postgresql/schemas/core/queries.js.map +1 -0
- package/dist/adapters/postgresql/schemas/core/transactions.d.ts +149 -0
- package/dist/adapters/postgresql/schemas/core/transactions.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/core/transactions.js +239 -0
- package/dist/adapters/postgresql/schemas/core/transactions.js.map +1 -0
- package/dist/adapters/postgresql/schemas/cron.d.ts +12 -12
- package/dist/adapters/postgresql/schemas/cron.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/cron.js +38 -10
- package/dist/adapters/postgresql/schemas/cron.js.map +1 -1
- package/dist/adapters/postgresql/schemas/extensions/citext.d.ts +222 -0
- package/dist/adapters/postgresql/schemas/extensions/citext.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/citext.js +306 -0
- package/dist/adapters/postgresql/schemas/extensions/citext.js.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/index.d.ts +15 -0
- package/dist/adapters/postgresql/schemas/extensions/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/index.js +20 -0
- package/dist/adapters/postgresql/schemas/extensions/index.js.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/kcache.d.ts +164 -0
- package/dist/adapters/postgresql/schemas/extensions/kcache.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/kcache.js +225 -0
- package/dist/adapters/postgresql/schemas/extensions/kcache.js.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/ltree.d.ts +253 -0
- package/dist/adapters/postgresql/schemas/extensions/ltree.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/ltree.js +430 -0
- package/dist/adapters/postgresql/schemas/extensions/ltree.js.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/pgcrypto.d.ts +251 -0
- package/dist/adapters/postgresql/schemas/extensions/pgcrypto.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/pgcrypto.js +294 -0
- package/dist/adapters/postgresql/schemas/extensions/pgcrypto.js.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/shared.d.ts +10 -0
- package/dist/adapters/postgresql/schemas/extensions/shared.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/extensions/shared.js +15 -0
- package/dist/adapters/postgresql/schemas/extensions/shared.js.map +1 -0
- package/dist/adapters/postgresql/schemas/index.d.ts +6 -6
- package/dist/adapters/postgresql/schemas/index.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/index.js +8 -8
- package/dist/adapters/postgresql/schemas/index.js.map +1 -1
- package/dist/adapters/postgresql/schemas/introspection.d.ts +14 -14
- package/dist/adapters/postgresql/schemas/introspection.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/introspection.js +6 -3
- package/dist/adapters/postgresql/schemas/introspection.js.map +1 -1
- package/dist/adapters/postgresql/schemas/jsonb/advanced.d.ts +270 -0
- package/dist/adapters/postgresql/schemas/jsonb/advanced.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/jsonb/advanced.js +371 -0
- package/dist/adapters/postgresql/schemas/jsonb/advanced.js.map +1 -0
- package/dist/adapters/postgresql/schemas/jsonb/basic.d.ts +283 -0
- package/dist/adapters/postgresql/schemas/jsonb/basic.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/jsonb/basic.js +456 -0
- package/dist/adapters/postgresql/schemas/jsonb/basic.js.map +1 -0
- package/dist/adapters/postgresql/schemas/jsonb/index.d.ts +6 -0
- package/dist/adapters/postgresql/schemas/jsonb/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/jsonb/index.js +6 -0
- package/dist/adapters/postgresql/schemas/jsonb/index.js.map +1 -0
- package/dist/adapters/postgresql/schemas/monitoring.d.ts +4 -4
- package/dist/adapters/postgresql/schemas/monitoring.js +2 -2
- package/dist/adapters/postgresql/schemas/monitoring.js.map +1 -1
- package/dist/adapters/postgresql/schemas/partitioning.d.ts +14 -14
- package/dist/adapters/postgresql/schemas/partitioning.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/partitioning.js +64 -46
- package/dist/adapters/postgresql/schemas/partitioning.js.map +1 -1
- package/dist/adapters/postgresql/schemas/partman.d.ts +16 -14
- package/dist/adapters/postgresql/schemas/partman.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/partman.js +9 -9
- package/dist/adapters/postgresql/schemas/partman.js.map +1 -1
- package/dist/adapters/postgresql/schemas/postgis/advanced.d.ts +429 -0
- package/dist/adapters/postgresql/schemas/postgis/advanced.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/postgis/advanced.js +495 -0
- package/dist/adapters/postgresql/schemas/postgis/advanced.js.map +1 -0
- package/dist/adapters/postgresql/schemas/{postgis.d.ts → postgis/basic.d.ts} +1 -423
- package/dist/adapters/postgresql/schemas/postgis/basic.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/{postgis.js → postgis/basic.js} +1 -486
- package/dist/adapters/postgresql/schemas/postgis/basic.js.map +1 -0
- package/dist/adapters/postgresql/schemas/postgis/index.d.ts +6 -0
- package/dist/adapters/postgresql/schemas/postgis/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/postgis/index.js +6 -0
- package/dist/adapters/postgresql/schemas/postgis/index.js.map +1 -0
- package/dist/adapters/postgresql/schemas/schema-mgmt.d.ts +35 -25
- package/dist/adapters/postgresql/schemas/schema-mgmt.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/schema-mgmt.js +57 -19
- package/dist/adapters/postgresql/schemas/schema-mgmt.js.map +1 -1
- package/dist/adapters/postgresql/schemas/stats/index.d.ts +6 -0
- package/dist/adapters/postgresql/schemas/stats/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/stats/index.js +6 -0
- package/dist/adapters/postgresql/schemas/stats/index.js.map +1 -0
- package/dist/adapters/postgresql/schemas/stats/input.d.ts +260 -0
- package/dist/adapters/postgresql/schemas/stats/input.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/{stats.js → stats/input.js} +2 -331
- package/dist/adapters/postgresql/schemas/stats/input.js.map +1 -0
- package/dist/adapters/postgresql/schemas/{stats.d.ts → stats/output.d.ts} +3 -246
- package/dist/adapters/postgresql/schemas/stats/output.d.ts.map +1 -0
- package/dist/adapters/postgresql/schemas/stats/output.js +334 -0
- package/dist/adapters/postgresql/schemas/stats/output.js.map +1 -0
- package/dist/adapters/postgresql/schemas/text-search.d.ts +18 -18
- package/dist/adapters/postgresql/schemas/text-search.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/text-search.js +12 -27
- package/dist/adapters/postgresql/schemas/text-search.js.map +1 -1
- package/dist/adapters/postgresql/schemas/vector.d.ts +10 -10
- package/dist/adapters/postgresql/schemas/vector.d.ts.map +1 -1
- package/dist/adapters/postgresql/schemas/vector.js +12 -16
- package/dist/adapters/postgresql/schemas/vector.js.map +1 -1
- package/dist/adapters/postgresql/tools/backup/dump.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/backup/dump.js +95 -76
- package/dist/adapters/postgresql/tools/backup/dump.js.map +1 -1
- package/dist/adapters/postgresql/tools/backup/planning.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/backup/planning.js +345 -287
- package/dist/adapters/postgresql/tools/backup/planning.js.map +1 -1
- package/dist/adapters/postgresql/tools/citext/analysis.d.ts +24 -0
- package/dist/adapters/postgresql/tools/citext/analysis.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/{citext.js → citext/analysis.js} +50 -232
- package/dist/adapters/postgresql/tools/citext/analysis.js.map +1 -0
- package/dist/adapters/postgresql/tools/citext/index.d.ts +15 -0
- package/dist/adapters/postgresql/tools/citext/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/citext/index.js +23 -0
- package/dist/adapters/postgresql/tools/citext/index.js.map +1 -0
- package/dist/adapters/postgresql/tools/citext/setup.d.ts +16 -0
- package/dist/adapters/postgresql/tools/citext/setup.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/citext/setup.js +193 -0
- package/dist/adapters/postgresql/tools/citext/setup.js.map +1 -0
- package/dist/adapters/postgresql/tools/codemode/index.js +1 -1
- package/dist/adapters/postgresql/tools/codemode/index.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/convenience.d.ts +12 -22
- package/dist/adapters/postgresql/tools/core/convenience.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/convenience.js +100 -210
- package/dist/adapters/postgresql/tools/core/convenience.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/error-helpers.d.ts +1 -0
- package/dist/adapters/postgresql/tools/core/error-helpers.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/error-helpers.js +8 -1
- package/dist/adapters/postgresql/tools/core/error-helpers.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/health.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/health.js +124 -114
- package/dist/adapters/postgresql/tools/core/health.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/index.d.ts +2 -1
- package/dist/adapters/postgresql/tools/core/index.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/index.js +3 -2
- package/dist/adapters/postgresql/tools/core/index.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/indexes.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/indexes.js +151 -127
- package/dist/adapters/postgresql/tools/core/indexes.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/objects.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/objects.js +186 -161
- package/dist/adapters/postgresql/tools/core/objects.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/query.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/query.js +37 -25
- package/dist/adapters/postgresql/tools/core/query.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/schemas.d.ts +6 -3
- package/dist/adapters/postgresql/tools/core/schemas.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/schemas.js +11 -2
- package/dist/adapters/postgresql/tools/core/schemas.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/tables.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/core/tables.js +156 -129
- package/dist/adapters/postgresql/tools/core/tables.js.map +1 -1
- package/dist/adapters/postgresql/tools/core/utility.d.ts +26 -0
- package/dist/adapters/postgresql/tools/core/utility.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/core/utility.js +174 -0
- package/dist/adapters/postgresql/tools/core/utility.js.map +1 -0
- package/dist/adapters/postgresql/tools/cron.js +90 -43
- package/dist/adapters/postgresql/tools/cron.js.map +1 -1
- package/dist/adapters/postgresql/tools/introspection/analysis.d.ts +12 -0
- package/dist/adapters/postgresql/tools/introspection/analysis.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/introspection/analysis.js +574 -0
- package/dist/adapters/postgresql/tools/introspection/analysis.js.map +1 -0
- package/dist/adapters/postgresql/tools/introspection/graph.d.ts +55 -0
- package/dist/adapters/postgresql/tools/introspection/graph.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/introspection/graph.js +638 -0
- package/dist/adapters/postgresql/tools/introspection/graph.js.map +1 -0
- package/dist/adapters/postgresql/tools/introspection/index.d.ts +19 -0
- package/dist/adapters/postgresql/tools/introspection/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/introspection/index.js +36 -0
- package/dist/adapters/postgresql/tools/introspection/index.js.map +1 -0
- package/dist/adapters/postgresql/tools/introspection/migration.d.ts +15 -0
- package/dist/adapters/postgresql/tools/introspection/migration.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/introspection/migration.js +599 -0
- package/dist/adapters/postgresql/tools/introspection/migration.js.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/analytics.d.ts +20 -0
- package/dist/adapters/postgresql/tools/jsonb/analytics.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/analytics.js +367 -0
- package/dist/adapters/postgresql/tools/jsonb/analytics.js.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/index.d.ts +4 -2
- package/dist/adapters/postgresql/tools/jsonb/index.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/jsonb/index.js +8 -4
- package/dist/adapters/postgresql/tools/jsonb/index.js.map +1 -1
- package/dist/adapters/postgresql/tools/jsonb/read.d.ts +38 -0
- package/dist/adapters/postgresql/tools/jsonb/read.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/{basic.js → read.js} +41 -482
- package/dist/adapters/postgresql/tools/jsonb/read.js.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/{advanced.d.ts → transform.d.ts} +1 -13
- package/dist/adapters/postgresql/tools/jsonb/transform.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/{advanced.js → transform.js} +26 -357
- package/dist/adapters/postgresql/tools/jsonb/transform.js.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/write.d.ts +14 -0
- package/dist/adapters/postgresql/tools/jsonb/write.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/jsonb/write.js +468 -0
- package/dist/adapters/postgresql/tools/jsonb/write.js.map +1 -0
- package/dist/adapters/postgresql/tools/kcache.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/kcache.js +116 -51
- package/dist/adapters/postgresql/tools/kcache.js.map +1 -1
- package/dist/adapters/postgresql/tools/ltree.js +346 -260
- package/dist/adapters/postgresql/tools/ltree.js.map +1 -1
- package/dist/adapters/postgresql/tools/monitoring/analysis.d.ts +15 -0
- package/dist/adapters/postgresql/tools/monitoring/analysis.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/{monitoring.js → monitoring/analysis.js} +24 -359
- package/dist/adapters/postgresql/tools/monitoring/analysis.js.map +1 -0
- package/dist/adapters/postgresql/tools/monitoring/basic.d.ts +17 -0
- package/dist/adapters/postgresql/tools/monitoring/basic.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/monitoring/basic.js +432 -0
- package/dist/adapters/postgresql/tools/monitoring/basic.js.map +1 -0
- package/dist/adapters/postgresql/tools/monitoring/index.d.ts +16 -0
- package/dist/adapters/postgresql/tools/monitoring/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/monitoring/index.js +31 -0
- package/dist/adapters/postgresql/tools/monitoring/index.js.map +1 -0
- package/dist/adapters/postgresql/tools/partitioning/index.d.ts +15 -0
- package/dist/adapters/postgresql/tools/partitioning/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/partitioning/index.js +23 -0
- package/dist/adapters/postgresql/tools/partitioning/index.js.map +1 -0
- package/dist/adapters/postgresql/tools/partitioning/info.d.ts +11 -0
- package/dist/adapters/postgresql/tools/partitioning/info.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/partitioning/info.js +302 -0
- package/dist/adapters/postgresql/tools/partitioning/info.js.map +1 -0
- package/dist/adapters/postgresql/tools/partitioning/management.d.ts +28 -0
- package/dist/adapters/postgresql/tools/partitioning/management.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/{partitioning.js → partitioning/management.js} +48 -307
- package/dist/adapters/postgresql/tools/partitioning/management.js.map +1 -0
- package/dist/adapters/postgresql/tools/partman/helpers.d.ts +29 -0
- package/dist/adapters/postgresql/tools/partman/helpers.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/partman/helpers.js +59 -0
- package/dist/adapters/postgresql/tools/partman/helpers.js.map +1 -0
- package/dist/adapters/postgresql/tools/partman/index.d.ts +2 -1
- package/dist/adapters/postgresql/tools/partman/index.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/partman/index.js +4 -2
- package/dist/adapters/postgresql/tools/partman/index.js.map +1 -1
- package/dist/adapters/postgresql/tools/partman/maintenance.d.ts +20 -0
- package/dist/adapters/postgresql/tools/partman/maintenance.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/partman/maintenance.js +496 -0
- package/dist/adapters/postgresql/tools/partman/maintenance.js.map +1 -0
- package/dist/adapters/postgresql/tools/partman/management.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/partman/management.js +438 -383
- package/dist/adapters/postgresql/tools/partman/management.js.map +1 -1
- package/dist/adapters/postgresql/tools/partman/operations.d.ts +1 -13
- package/dist/adapters/postgresql/tools/partman/operations.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/partman/operations.js +171 -652
- package/dist/adapters/postgresql/tools/partman/operations.js.map +1 -1
- package/dist/adapters/postgresql/tools/performance/analysis.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/performance/analysis.js +69 -42
- package/dist/adapters/postgresql/tools/performance/analysis.js.map +1 -1
- package/dist/adapters/postgresql/tools/performance/monitoring.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/performance/monitoring.js +80 -55
- package/dist/adapters/postgresql/tools/performance/monitoring.js.map +1 -1
- package/dist/adapters/postgresql/tools/performance/optimization.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/performance/optimization.js +18 -11
- package/dist/adapters/postgresql/tools/performance/optimization.js.map +1 -1
- package/dist/adapters/postgresql/tools/performance/stats.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/performance/stats.js +439 -318
- package/dist/adapters/postgresql/tools/performance/stats.js.map +1 -1
- package/dist/adapters/postgresql/tools/pgcrypto.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/pgcrypto.js +45 -77
- package/dist/adapters/postgresql/tools/pgcrypto.js.map +1 -1
- package/dist/adapters/postgresql/tools/postgis/basic.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/postgis/basic.js +121 -93
- package/dist/adapters/postgresql/tools/postgis/basic.js.map +1 -1
- package/dist/adapters/postgresql/tools/schema/index.d.ts +16 -0
- package/dist/adapters/postgresql/tools/schema/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/schema/index.js +32 -0
- package/dist/adapters/postgresql/tools/schema/index.js.map +1 -0
- package/dist/adapters/postgresql/tools/schema/objects.d.ts +15 -0
- package/dist/adapters/postgresql/tools/schema/objects.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/schema/objects.js +378 -0
- package/dist/adapters/postgresql/tools/schema/objects.js.map +1 -0
- package/dist/adapters/postgresql/tools/schema/views.d.ts +15 -0
- package/dist/adapters/postgresql/tools/schema/views.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/{schema.js → schema/views.js} +64 -386
- package/dist/adapters/postgresql/tools/schema/views.js.map +1 -0
- package/dist/adapters/postgresql/tools/stats/advanced.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/stats/advanced.js +1 -218
- package/dist/adapters/postgresql/tools/stats/advanced.js.map +1 -1
- package/dist/adapters/postgresql/tools/stats/math-utils.d.ts +33 -0
- package/dist/adapters/postgresql/tools/stats/math-utils.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/stats/math-utils.js +225 -0
- package/dist/adapters/postgresql/tools/stats/math-utils.js.map +1 -0
- package/dist/adapters/postgresql/tools/text/index.d.ts +16 -0
- package/dist/adapters/postgresql/tools/text/index.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/text/index.js +33 -0
- package/dist/adapters/postgresql/tools/text/index.js.map +1 -0
- package/dist/adapters/postgresql/tools/text/matching.d.ts +17 -0
- package/dist/adapters/postgresql/tools/text/matching.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/text/matching.js +565 -0
- package/dist/adapters/postgresql/tools/text/matching.js.map +1 -0
- package/dist/adapters/postgresql/tools/text/search.d.ts +17 -0
- package/dist/adapters/postgresql/tools/text/search.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/text/search.js +653 -0
- package/dist/adapters/postgresql/tools/text/search.js.map +1 -0
- package/dist/adapters/postgresql/tools/transactions.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/transactions.js +11 -27
- package/dist/adapters/postgresql/tools/transactions.js.map +1 -1
- package/dist/adapters/postgresql/tools/vector/{basic.d.ts → data.d.ts} +10 -8
- package/dist/adapters/postgresql/tools/vector/data.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/vector/data.js +540 -0
- package/dist/adapters/postgresql/tools/vector/data.js.map +1 -0
- package/dist/adapters/postgresql/tools/vector/index.d.ts.map +1 -1
- package/dist/adapters/postgresql/tools/vector/index.js +6 -2
- package/dist/adapters/postgresql/tools/vector/index.js.map +1 -1
- package/dist/adapters/postgresql/tools/vector/management.d.ts +11 -0
- package/dist/adapters/postgresql/tools/vector/management.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/vector/management.js +425 -0
- package/dist/adapters/postgresql/tools/vector/management.js.map +1 -0
- package/dist/adapters/postgresql/tools/vector/query.d.ts +14 -0
- package/dist/adapters/postgresql/tools/vector/query.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/vector/query.js +767 -0
- package/dist/adapters/postgresql/tools/vector/query.js.map +1 -0
- package/dist/adapters/postgresql/tools/vector/{advanced.d.ts → search-advanced.d.ts} +4 -5
- package/dist/adapters/postgresql/tools/vector/search-advanced.d.ts.map +1 -0
- package/dist/adapters/postgresql/tools/vector/search-advanced.js +626 -0
- package/dist/adapters/postgresql/tools/vector/search-advanced.js.map +1 -0
- package/dist/auth/scopes.js +1 -1
- package/dist/auth/scopes.js.map +1 -1
- package/dist/cli/args.d.ts +3 -2
- package/dist/cli/args.d.ts.map +1 -1
- package/dist/cli/args.js +4 -3
- package/dist/cli/args.js.map +1 -1
- package/dist/cli.js +10 -4
- package/dist/cli.js.map +1 -1
- package/dist/codemode/api/aliases.d.ts +14 -0
- package/dist/codemode/api/aliases.d.ts.map +1 -0
- package/dist/codemode/api/aliases.js +503 -0
- package/dist/codemode/api/aliases.js.map +1 -0
- package/dist/codemode/api/group-api.d.ts +23 -0
- package/dist/codemode/api/group-api.d.ts.map +1 -0
- package/dist/codemode/api/group-api.js +179 -0
- package/dist/codemode/api/group-api.js.map +1 -0
- package/dist/codemode/{api.d.ts → api/index.d.ts} +4 -4
- package/dist/codemode/api/index.d.ts.map +1 -0
- package/dist/codemode/api/index.js +192 -0
- package/dist/codemode/api/index.js.map +1 -0
- package/dist/codemode/api/maps.d.ts +47 -0
- package/dist/codemode/api/maps.d.ts.map +1 -0
- package/dist/codemode/api/maps.js +523 -0
- package/dist/codemode/api/maps.js.map +1 -0
- package/dist/codemode/api/normalize.d.ts +13 -0
- package/dist/codemode/api/normalize.d.ts.map +1 -0
- package/dist/codemode/api/normalize.js +120 -0
- package/dist/codemode/api/normalize.js.map +1 -0
- package/dist/codemode/index.d.ts +1 -1
- package/dist/codemode/index.d.ts.map +1 -1
- package/dist/codemode/index.js +1 -1
- package/dist/codemode/index.js.map +1 -1
- package/dist/codemode/sandbox.d.ts.map +1 -1
- package/dist/codemode/sandbox.js +8 -25
- package/dist/codemode/sandbox.js.map +1 -1
- package/dist/server/McpServer.d.ts +1 -1
- package/dist/server/McpServer.d.ts.map +1 -1
- package/dist/server/McpServer.js +1 -2
- package/dist/server/McpServer.js.map +1 -1
- package/dist/transports/http.d.ts +43 -10
- package/dist/transports/http.d.ts.map +1 -1
- package/dist/transports/http.js +282 -49
- package/dist/transports/http.js.map +1 -1
- package/dist/utils/logger.d.ts +6 -6
- package/dist/utils/logger.d.ts.map +1 -1
- package/dist/utils/logger.js +18 -15
- package/dist/utils/logger.js.map +1 -1
- package/dist/utils/progress-utils.d.ts +2 -2
- package/dist/utils/progress-utils.d.ts.map +1 -1
- package/dist/utils/progress-utils.js +2 -3
- package/dist/utils/progress-utils.js.map +1 -1
- package/dist/utils/version.d.ts +9 -0
- package/dist/utils/version.d.ts.map +1 -0
- package/dist/utils/version.js +12 -0
- package/dist/utils/version.js.map +1 -0
- package/dist/utils/where-clause.d.ts +4 -0
- package/dist/utils/where-clause.d.ts.map +1 -1
- package/dist/utils/where-clause.js +16 -0
- package/dist/utils/where-clause.js.map +1 -1
- package/package.json +6 -4
- package/dist/adapters/postgresql/schemas/core.d.ts.map +0 -1
- package/dist/adapters/postgresql/schemas/core.js.map +0 -1
- package/dist/adapters/postgresql/schemas/extensions.d.ts +0 -852
- package/dist/adapters/postgresql/schemas/extensions.d.ts.map +0 -1
- package/dist/adapters/postgresql/schemas/extensions.js +0 -1202
- package/dist/adapters/postgresql/schemas/extensions.js.map +0 -1
- package/dist/adapters/postgresql/schemas/jsonb.d.ts +0 -541
- package/dist/adapters/postgresql/schemas/jsonb.d.ts.map +0 -1
- package/dist/adapters/postgresql/schemas/jsonb.js +0 -814
- package/dist/adapters/postgresql/schemas/jsonb.js.map +0 -1
- package/dist/adapters/postgresql/schemas/postgis.d.ts.map +0 -1
- package/dist/adapters/postgresql/schemas/postgis.js.map +0 -1
- package/dist/adapters/postgresql/schemas/stats.d.ts.map +0 -1
- package/dist/adapters/postgresql/schemas/stats.js.map +0 -1
- package/dist/adapters/postgresql/tools/citext.d.ts +0 -18
- package/dist/adapters/postgresql/tools/citext.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/citext.js.map +0 -1
- package/dist/adapters/postgresql/tools/introspection.d.ts +0 -15
- package/dist/adapters/postgresql/tools/introspection.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/introspection.js +0 -1682
- package/dist/adapters/postgresql/tools/introspection.js.map +0 -1
- package/dist/adapters/postgresql/tools/jsonb/advanced.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/jsonb/advanced.js.map +0 -1
- package/dist/adapters/postgresql/tools/jsonb/basic.d.ts +0 -20
- package/dist/adapters/postgresql/tools/jsonb/basic.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/jsonb/basic.js.map +0 -1
- package/dist/adapters/postgresql/tools/monitoring.d.ts +0 -13
- package/dist/adapters/postgresql/tools/monitoring.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/monitoring.js.map +0 -1
- package/dist/adapters/postgresql/tools/partitioning.d.ts +0 -13
- package/dist/adapters/postgresql/tools/partitioning.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/partitioning.js.map +0 -1
- package/dist/adapters/postgresql/tools/schema.d.ts +0 -13
- package/dist/adapters/postgresql/tools/schema.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/schema.js.map +0 -1
- package/dist/adapters/postgresql/tools/text.d.ts +0 -13
- package/dist/adapters/postgresql/tools/text.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/text.js +0 -1082
- package/dist/adapters/postgresql/tools/text.js.map +0 -1
- package/dist/adapters/postgresql/tools/vector/advanced.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/vector/advanced.js +0 -958
- package/dist/adapters/postgresql/tools/vector/advanced.js.map +0 -1
- package/dist/adapters/postgresql/tools/vector/basic.d.ts.map +0 -1
- package/dist/adapters/postgresql/tools/vector/basic.js +0 -1165
- package/dist/adapters/postgresql/tools/vector/basic.js.map +0 -1
- package/dist/codemode/api.d.ts.map +0 -1
- package/dist/codemode/api.js +0 -1544
- package/dist/codemode/api.js.map +0 -1
|
@@ -1,67 +1,13 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* PostgreSQL pg_partman Extension Tools - Operations
|
|
3
3
|
*
|
|
4
|
-
* Partition operations: check_default, partition_data
|
|
4
|
+
* Partition data operations: check_default, partition_data.
|
|
5
5
|
*/
|
|
6
|
-
import {
|
|
7
|
-
import { readOnly, write, destructive } from "../../../../utils/annotations.js";
|
|
6
|
+
import { readOnly, write } from "../../../../utils/annotations.js";
|
|
8
7
|
import { getToolIcons } from "../../../../utils/icons.js";
|
|
9
|
-
import {
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
/**
|
|
13
|
-
* Detect the schema where pg_partman is installed.
|
|
14
|
-
* Newer versions install to 'public' by default, older versions use 'partman'.
|
|
15
|
-
*/
|
|
16
|
-
async function getPartmanSchema(adapter) {
|
|
17
|
-
const result = await adapter.executeQuery(`
|
|
18
|
-
SELECT table_schema FROM information_schema.tables
|
|
19
|
-
WHERE table_name = 'part_config'
|
|
20
|
-
AND table_schema IN ('partman', 'public')
|
|
21
|
-
LIMIT 1
|
|
22
|
-
`);
|
|
23
|
-
return result.rows?.[0]?.["table_schema"] ?? "partman";
|
|
24
|
-
}
|
|
25
|
-
/**
|
|
26
|
-
* Ensure the 'partman' schema alias exists when pg_partman is installed in 'public'.
|
|
27
|
-
*
|
|
28
|
-
* pg_partman's partition_data_time function contains a hardcoded fully-qualified
|
|
29
|
-
* call to 'partman.check_control_type(...)'. When pg_partman is installed in
|
|
30
|
-
* the 'public' schema (the default for newer versions), this fails with
|
|
31
|
-
* 'schema "partman" does not exist'. Since the reference is fully-qualified,
|
|
32
|
-
* SET search_path cannot resolve it.
|
|
33
|
-
*
|
|
34
|
-
* This function creates the 'partman' schema if needed and adds a thin wrapper
|
|
35
|
-
* function that delegates to public.check_control_type().
|
|
36
|
-
*/
|
|
37
|
-
async function ensurePartmanSchemaAlias(adapter) {
|
|
38
|
-
try {
|
|
39
|
-
await adapter.executeQuery("CREATE SCHEMA IF NOT EXISTS partman");
|
|
40
|
-
await adapter.executeQuery(`
|
|
41
|
-
CREATE OR REPLACE FUNCTION partman.check_control_type(
|
|
42
|
-
p_parent_schema text, p_parent_tablename text, p_control text
|
|
43
|
-
) RETURNS TABLE(general_type text, exact_type text)
|
|
44
|
-
LANGUAGE sql STABLE AS $$
|
|
45
|
-
SELECT * FROM public.check_control_type(p_parent_schema, p_parent_tablename, p_control)
|
|
46
|
-
$$
|
|
47
|
-
`);
|
|
48
|
-
}
|
|
49
|
-
catch {
|
|
50
|
-
// Schema creation may fail due to permissions — proceed anyway,
|
|
51
|
-
// the actual CALL will produce its own clear error
|
|
52
|
-
}
|
|
53
|
-
}
|
|
54
|
-
/**
|
|
55
|
-
* Execute a pg_partman PROCEDURE, ensuring schema aliases are in place.
|
|
56
|
-
*/
|
|
57
|
-
async function callPartmanProcedure(adapter, partmanSchema, sql) {
|
|
58
|
-
// When pg_partman is installed in 'public', ensure the 'partman' schema alias
|
|
59
|
-
// exists for hardcoded partman.* references inside pg_partman's functions
|
|
60
|
-
if (partmanSchema === "public") {
|
|
61
|
-
await ensurePartmanSchemaAlias(adapter);
|
|
62
|
-
}
|
|
63
|
-
await adapter.executeQuery(sql);
|
|
64
|
-
}
|
|
8
|
+
import { formatPostgresError } from "../core/error-helpers.js";
|
|
9
|
+
import { PartmanCheckDefaultSchema, PartmanCheckDefaultSchemaBase, PartmanPartitionDataSchema, PartmanPartitionDataSchemaBase, PartmanCheckDefaultOutputSchema, PartmanPartitionDataOutputSchema, } from "../../schemas/index.js";
|
|
10
|
+
import { getPartmanSchema, callPartmanProcedure } from "./helpers.js";
|
|
65
11
|
/**
|
|
66
12
|
* Check for data in default partition
|
|
67
13
|
*/
|
|
@@ -76,33 +22,34 @@ Data in default indicates partitions may be missing for certain time/value range
|
|
|
76
22
|
annotations: readOnly("Check Partman Default"),
|
|
77
23
|
icons: getToolIcons("partman", readOnly("Check Partman Default")),
|
|
78
24
|
handler: async (params, _context) => {
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
25
|
+
try {
|
|
26
|
+
const { parentTable } = PartmanCheckDefaultSchema.parse(params);
|
|
27
|
+
// parentTable is required - provide clear error if missing
|
|
28
|
+
if (!parentTable) {
|
|
29
|
+
return {
|
|
30
|
+
success: false,
|
|
31
|
+
error: 'parentTable parameter is required. Specify the parent table (e.g., "public.events") to check its default partition.',
|
|
32
|
+
hint: "Use pg_partman_show_config to list all partition sets first.",
|
|
33
|
+
};
|
|
34
|
+
}
|
|
35
|
+
// Check if parent table exists in pg_class (handles orphaned configs)
|
|
36
|
+
const [tableSchema, tableName] = parentTable.includes(".")
|
|
37
|
+
? [parentTable.split(".")[0], parentTable.split(".")[1]]
|
|
38
|
+
: ["public", parentTable];
|
|
39
|
+
const tableExistsResult = await adapter.executeQuery(`
|
|
40
|
+
SELECT 1 FROM information_schema.tables
|
|
94
41
|
WHERE table_schema = $1 AND table_name = $2
|
|
95
42
|
`, [tableSchema, tableName]);
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
SELECT
|
|
43
|
+
if ((tableExistsResult.rows?.length ?? 0) === 0) {
|
|
44
|
+
return {
|
|
45
|
+
success: false,
|
|
46
|
+
error: `Table '${parentTable}' does not exist. Cannot check default partition for non-existent table.`,
|
|
47
|
+
hint: "Verify the table name or use pg_partman_show_config to list existing partition sets.",
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
// First, find the default partition
|
|
51
|
+
const findDefaultSql = `
|
|
52
|
+
SELECT
|
|
106
53
|
c.relname as default_partition,
|
|
107
54
|
n.nspname as schema
|
|
108
55
|
FROM pg_inherits i
|
|
@@ -113,82 +60,93 @@ Data in default indicates partitions may be missing for certain time/value range
|
|
|
113
60
|
WHERE (pn.nspname || '.' || p.relname) = $1
|
|
114
61
|
AND c.relname LIKE '%_default'
|
|
115
62
|
`;
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
63
|
+
const result = await adapter.executeQuery(findDefaultSql, [
|
|
64
|
+
parentTable,
|
|
65
|
+
]);
|
|
66
|
+
const defaultInfo = result.rows?.[0];
|
|
67
|
+
if (!defaultInfo) {
|
|
68
|
+
// Check if the table is partitioned at all (has any child tables)
|
|
69
|
+
const hasChildrenResult = await adapter.executeQuery(`
|
|
121
70
|
SELECT 1 FROM pg_inherits i
|
|
122
71
|
JOIN pg_class p ON p.oid = i.inhparent
|
|
123
72
|
JOIN pg_namespace pn ON pn.oid = p.relnamespace
|
|
124
73
|
WHERE (pn.nspname || '.' || p.relname) = $1
|
|
125
74
|
LIMIT 1
|
|
126
75
|
`, [parentTable]);
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
76
|
+
// Also check if the table is actually a partitioned table (relkind = 'p')
|
|
77
|
+
const [tableSchema, tableName] = parentTable.includes(".")
|
|
78
|
+
? [parentTable.split(".")[0], parentTable.split(".")[1]]
|
|
79
|
+
: ["public", parentTable];
|
|
80
|
+
const partitionedCheckResult = await adapter.executeQuery(`
|
|
132
81
|
SELECT relkind FROM pg_class c
|
|
133
82
|
JOIN pg_namespace n ON n.oid = c.relnamespace
|
|
134
83
|
WHERE n.nspname = $1 AND c.relname = $2
|
|
135
84
|
`, [tableSchema, tableName]);
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
85
|
+
const relkind = partitionedCheckResult.rows?.[0]?.["relkind"];
|
|
86
|
+
const isActuallyPartitioned = relkind === "p"; // 'p' means partitioned table
|
|
87
|
+
if ((hasChildrenResult.rows?.length ?? 0) === 0) {
|
|
88
|
+
if (isActuallyPartitioned) {
|
|
89
|
+
return {
|
|
90
|
+
success: true,
|
|
91
|
+
parentTable,
|
|
92
|
+
hasDefault: false,
|
|
93
|
+
isPartitioned: true,
|
|
94
|
+
hasChildPartitions: false,
|
|
95
|
+
message: "Table is partitioned but has no child partitions yet. Run pg_partman_run_maintenance or insert data to create partitions. " +
|
|
96
|
+
"TIP: For empty tables, configure pg_partman with startPartition before running maintenance.",
|
|
97
|
+
};
|
|
98
|
+
}
|
|
140
99
|
return {
|
|
141
100
|
success: true,
|
|
142
101
|
parentTable,
|
|
143
102
|
hasDefault: false,
|
|
144
|
-
isPartitioned:
|
|
103
|
+
isPartitioned: false,
|
|
145
104
|
hasChildPartitions: false,
|
|
146
|
-
message: "Table is
|
|
147
|
-
"TIP: For empty tables, configure pg_partman with startPartition before running maintenance.",
|
|
105
|
+
message: "Table is not a partitioned table. Create it with PARTITION BY clause to enable partitioning.",
|
|
148
106
|
};
|
|
149
107
|
}
|
|
150
108
|
return {
|
|
151
109
|
success: true,
|
|
152
110
|
parentTable,
|
|
153
111
|
hasDefault: false,
|
|
154
|
-
isPartitioned:
|
|
155
|
-
hasChildPartitions:
|
|
156
|
-
message: "Table is
|
|
112
|
+
isPartitioned: true,
|
|
113
|
+
hasChildPartitions: true,
|
|
114
|
+
message: "Table is partitioned with child partitions but has no default partition. This is normal if the partition set was created without a default.",
|
|
157
115
|
};
|
|
158
116
|
}
|
|
117
|
+
const defaultPartitionName = `${String(defaultInfo["schema"])}.${String(defaultInfo["default_partition"])}`;
|
|
118
|
+
// Use actual COUNT for accuracy instead of reltuples (which returns -1 before ANALYZE)
|
|
119
|
+
// Limit to 1 for efficiency - we only need to know if ANY data exists
|
|
120
|
+
const countSql = `SELECT COUNT(*) FROM (SELECT 1 FROM ${defaultPartitionName} LIMIT 1) t`;
|
|
121
|
+
let rowCount;
|
|
122
|
+
try {
|
|
123
|
+
const countResult = await adapter.executeQuery(countSql);
|
|
124
|
+
rowCount = Number(countResult.rows?.[0]?.["count"] ?? 0);
|
|
125
|
+
}
|
|
126
|
+
catch {
|
|
127
|
+
// If count fails (rare), fall back to 0
|
|
128
|
+
rowCount = 0;
|
|
129
|
+
}
|
|
130
|
+
const hasData = rowCount > 0;
|
|
159
131
|
return {
|
|
160
132
|
success: true,
|
|
161
133
|
parentTable,
|
|
162
|
-
hasDefault:
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
134
|
+
hasDefault: true,
|
|
135
|
+
defaultPartition: defaultPartitionName,
|
|
136
|
+
hasDataInDefault: hasData,
|
|
137
|
+
recommendation: hasData
|
|
138
|
+
? "Run pg_partman_partition_data to move data to appropriate child partitions"
|
|
139
|
+
: "Default partition is empty - no action needed",
|
|
166
140
|
};
|
|
167
141
|
}
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
rowCount = Number(countResult.rows?.[0]?.["count"] ?? 0);
|
|
176
|
-
}
|
|
177
|
-
catch {
|
|
178
|
-
// If count fails (rare), fall back to 0
|
|
179
|
-
rowCount = 0;
|
|
142
|
+
catch (error) {
|
|
143
|
+
return {
|
|
144
|
+
success: false,
|
|
145
|
+
error: formatPostgresError(error, {
|
|
146
|
+
tool: "pg_partman_check_default",
|
|
147
|
+
}),
|
|
148
|
+
};
|
|
180
149
|
}
|
|
181
|
-
const hasData = rowCount > 0;
|
|
182
|
-
return {
|
|
183
|
-
success: true,
|
|
184
|
-
parentTable,
|
|
185
|
-
hasDefault: true,
|
|
186
|
-
defaultPartition: defaultPartitionName,
|
|
187
|
-
hasDataInDefault: hasData,
|
|
188
|
-
recommendation: hasData
|
|
189
|
-
? "Run pg_partman_partition_data to move data to appropriate child partitions"
|
|
190
|
-
: "Default partition is empty - no action needed",
|
|
191
|
-
};
|
|
192
150
|
},
|
|
193
151
|
};
|
|
194
152
|
}
|
|
@@ -206,546 +164,107 @@ Creates new partitions if needed for the data being moved.`,
|
|
|
206
164
|
annotations: write("Partition Data"),
|
|
207
165
|
icons: getToolIcons("partman", write("Partition Data")),
|
|
208
166
|
handler: async (params, _context) => {
|
|
209
|
-
const { parentTable, batchSize, lockWaitSeconds } = PartmanPartitionDataSchema.parse(params);
|
|
210
|
-
// parentTable is required - provide clear error if missing
|
|
211
|
-
if (!parentTable) {
|
|
212
|
-
return {
|
|
213
|
-
success: false,
|
|
214
|
-
error: 'parentTable parameter is required. Specify the parent table (e.g., "public.events") to move data from its default partition.',
|
|
215
|
-
hint: "Use pg_partman_show_config to list all partition sets first.",
|
|
216
|
-
};
|
|
217
|
-
}
|
|
218
|
-
const args = [`p_parent_table := '${parentTable}'`];
|
|
219
|
-
if (batchSize !== undefined) {
|
|
220
|
-
args.push(`p_loop_count := ${String(batchSize)}`);
|
|
221
|
-
}
|
|
222
|
-
if (lockWaitSeconds !== undefined) {
|
|
223
|
-
args.push(`p_lock_wait := ${String(lockWaitSeconds)}`);
|
|
224
|
-
}
|
|
225
|
-
const partmanSchema = await getPartmanSchema(adapter);
|
|
226
|
-
let configResult;
|
|
227
|
-
try {
|
|
228
|
-
configResult = await adapter.executeQuery(`
|
|
229
|
-
SELECT control, epoch
|
|
230
|
-
FROM ${partmanSchema}.part_config
|
|
231
|
-
WHERE parent_table = $1
|
|
232
|
-
`, [parentTable]);
|
|
233
|
-
}
|
|
234
|
-
catch {
|
|
235
|
-
return {
|
|
236
|
-
success: false,
|
|
237
|
-
error: "pg_partman extension not found or not properly installed.",
|
|
238
|
-
hint: "Install pg_partman with pg_partman_create_extension, then configure the partition set with pg_partman_create_parent.",
|
|
239
|
-
};
|
|
240
|
-
}
|
|
241
|
-
const config = configResult.rows?.[0];
|
|
242
|
-
if (!config) {
|
|
243
|
-
return {
|
|
244
|
-
success: false,
|
|
245
|
-
error: `No pg_partman configuration found for ${parentTable}`,
|
|
246
|
-
};
|
|
247
|
-
}
|
|
248
|
-
// Get row count in default partition before moving data
|
|
249
|
-
const [partSchema, partTableName] = parentTable.includes(".")
|
|
250
|
-
? [
|
|
251
|
-
parentTable.split(".")[0] ?? "public",
|
|
252
|
-
parentTable.split(".")[1] ?? parentTable,
|
|
253
|
-
]
|
|
254
|
-
: ["public", parentTable];
|
|
255
|
-
const defaultPartitionName = `${partSchema}.${partTableName}_default`;
|
|
256
|
-
let rowsBeforeMove = 0;
|
|
257
|
-
try {
|
|
258
|
-
const beforeResult = await adapter.executeQuery(`SELECT COUNT(*)::int as count FROM ${defaultPartitionName}`);
|
|
259
|
-
rowsBeforeMove = Number(beforeResult.rows?.[0]?.["count"] ?? 0);
|
|
260
|
-
}
|
|
261
|
-
catch {
|
|
262
|
-
// Default partition might not exist - that's okay
|
|
263
|
-
}
|
|
264
|
-
// partition_data_proc is a PROCEDURE, not a function - use CALL syntax
|
|
265
|
-
// Uses callPartmanProcedure to set search_path, resolving hardcoded
|
|
266
|
-
// 'partman.*' references inside pg_partman's internal functions
|
|
267
|
-
const sql = `CALL ${partmanSchema}.partition_data_proc(${args.join(", ")})`;
|
|
268
167
|
try {
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
const errorMsg = e instanceof Error ? e.message : String(e);
|
|
273
|
-
return {
|
|
274
|
-
success: false,
|
|
275
|
-
parentTable,
|
|
276
|
-
error: `Failed to move data from default partition: ${errorMsg.split("\n")[0] ?? errorMsg}`,
|
|
277
|
-
hint: "Ensure pg_partman is properly installed and the partition set is configured correctly. " +
|
|
278
|
-
"Use pg_partman_show_config to verify configuration.",
|
|
279
|
-
};
|
|
280
|
-
}
|
|
281
|
-
// Get row count in default partition after moving data
|
|
282
|
-
let rowsAfterMove = 0;
|
|
283
|
-
try {
|
|
284
|
-
const afterResult = await adapter.executeQuery(`SELECT COUNT(*)::int as count FROM ${defaultPartitionName}`);
|
|
285
|
-
rowsAfterMove = Number(afterResult.rows?.[0]?.["count"] ?? 0);
|
|
286
|
-
}
|
|
287
|
-
catch {
|
|
288
|
-
// Default partition might not exist
|
|
289
|
-
}
|
|
290
|
-
const rowsMoved = rowsBeforeMove - rowsAfterMove;
|
|
291
|
-
return {
|
|
292
|
-
success: true,
|
|
293
|
-
parentTable,
|
|
294
|
-
rowsMoved: rowsMoved > 0 ? rowsMoved : 0,
|
|
295
|
-
rowsRemaining: rowsAfterMove,
|
|
296
|
-
message: rowsMoved > 0
|
|
297
|
-
? `Data partitioning completed - ${String(rowsMoved)} rows moved from default to child partitions`
|
|
298
|
-
: "Data partitioning completed - no rows needed to be moved (default partition empty or already partitioned)",
|
|
299
|
-
};
|
|
300
|
-
},
|
|
301
|
-
};
|
|
302
|
-
}
|
|
303
|
-
/**
|
|
304
|
-
* Configure retention policies
|
|
305
|
-
*/
|
|
306
|
-
export function createPartmanSetRetentionTool(adapter) {
|
|
307
|
-
return {
|
|
308
|
-
name: "pg_partman_set_retention",
|
|
309
|
-
description: `Configure retention policy for a partition set.
|
|
310
|
-
Partitions older than the retention period will be dropped or detached during maintenance.`,
|
|
311
|
-
group: "partman",
|
|
312
|
-
inputSchema: PartmanRetentionSchemaBase,
|
|
313
|
-
outputSchema: PartmanSetRetentionOutputSchema,
|
|
314
|
-
annotations: write("Set Partition Retention"),
|
|
315
|
-
icons: getToolIcons("partman", write("Set Partition Retention")),
|
|
316
|
-
handler: async (params, _context) => {
|
|
317
|
-
const { parentTable, retention, retentionKeepTable } = PartmanRetentionSchema.parse(params);
|
|
318
|
-
// Validate required parentTable
|
|
319
|
-
if (!parentTable) {
|
|
320
|
-
return {
|
|
321
|
-
success: false,
|
|
322
|
-
error: "Missing required parameter: parentTable.",
|
|
323
|
-
hint: 'Example: pg_partman_set_retention({ parentTable: "public.events", retention: "30 days" })',
|
|
324
|
-
};
|
|
325
|
-
}
|
|
326
|
-
const validatedParentTable = parentTable;
|
|
327
|
-
const partmanSchema = await getPartmanSchema(adapter);
|
|
328
|
-
// If retention is omitted (undefined), it's required
|
|
329
|
-
if (retention === undefined) {
|
|
330
|
-
return {
|
|
331
|
-
success: false,
|
|
332
|
-
error: "Missing required parameter: retention.",
|
|
333
|
-
hint: 'Provide a retention period (e.g., "30 days") or pass null to explicitly disable retention. ' +
|
|
334
|
-
'Example: pg_partman_set_retention({ parentTable: "public.events", retention: "30 days" })',
|
|
335
|
-
};
|
|
336
|
-
}
|
|
337
|
-
// Special case: explicit null or empty string means disable/clear retention
|
|
338
|
-
if (retention === null || retention === "") {
|
|
339
|
-
const sql = `
|
|
340
|
-
UPDATE ${partmanSchema}.part_config
|
|
341
|
-
SET retention = NULL
|
|
342
|
-
WHERE parent_table = $1
|
|
343
|
-
`;
|
|
344
|
-
const result = await adapter.executeQuery(sql, [validatedParentTable]);
|
|
345
|
-
if ((result.rowsAffected ?? 0) === 0) {
|
|
168
|
+
const { parentTable, batchSize, lockWaitSeconds } = PartmanPartitionDataSchema.parse(params);
|
|
169
|
+
// parentTable is required - provide clear error if missing
|
|
170
|
+
if (!parentTable) {
|
|
346
171
|
return {
|
|
347
172
|
success: false,
|
|
348
|
-
error:
|
|
349
|
-
hint: "Use pg_partman_show_config to list
|
|
173
|
+
error: 'parentTable parameter is required. Specify the parent table (e.g., "public.events") to move data from its default partition.',
|
|
174
|
+
hint: "Use pg_partman_show_config to list all partition sets first.",
|
|
350
175
|
};
|
|
351
176
|
}
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
retention: null,
|
|
356
|
-
message: "Retention policy disabled - partitions will no longer be automatically dropped or detached",
|
|
357
|
-
};
|
|
358
|
-
}
|
|
359
|
-
const validatedRetention = retention;
|
|
360
|
-
// Validate retention format - must be valid PostgreSQL interval
|
|
361
|
-
// Try to parse it to catch obvious errors before storing garbage
|
|
362
|
-
const validIntervalPattern = /^\d+\s*(second|minute|hour|day|week|month|year)s?$/i;
|
|
363
|
-
const validNumericPattern = /^\d+$/; // Allow pure numeric for integer-based partitions
|
|
364
|
-
if (!validIntervalPattern.test(validatedRetention) &&
|
|
365
|
-
!validNumericPattern.test(validatedRetention)) {
|
|
366
|
-
return {
|
|
367
|
-
success: false,
|
|
368
|
-
error: `Invalid retention format '${validatedRetention}'.`,
|
|
369
|
-
hint: "Use PostgreSQL interval syntax (e.g., '30 days', '6 months', '1 year') " +
|
|
370
|
-
"or integer value for integer-based partitions.",
|
|
371
|
-
};
|
|
372
|
-
}
|
|
373
|
-
const updates = [`retention = '${validatedRetention}'`];
|
|
374
|
-
if (retentionKeepTable !== undefined) {
|
|
375
|
-
updates.push(`retention_keep_table = ${String(retentionKeepTable)}`);
|
|
376
|
-
}
|
|
377
|
-
const sql = `
|
|
378
|
-
UPDATE ${partmanSchema}.part_config
|
|
379
|
-
SET ${updates.join(", ")}
|
|
380
|
-
WHERE parent_table = $1
|
|
381
|
-
`;
|
|
382
|
-
const result = await adapter.executeQuery(sql, [validatedParentTable]);
|
|
383
|
-
if ((result.rowsAffected ?? 0) === 0) {
|
|
384
|
-
return {
|
|
385
|
-
success: false,
|
|
386
|
-
error: `No pg_partman configuration found for ${validatedParentTable}.`,
|
|
387
|
-
hint: "Use pg_partman_show_config to list existing partition sets.",
|
|
388
|
-
};
|
|
389
|
-
}
|
|
390
|
-
// Check partition type to use appropriate terminology in message
|
|
391
|
-
const configResult = await adapter.executeQuery(`SELECT partition_type FROM ${partmanSchema}.part_config WHERE parent_table = $1`, [validatedParentTable]);
|
|
392
|
-
const partitionTypeRaw = configResult.rows?.[0]?.["partition_type"];
|
|
393
|
-
const partitionType = typeof partitionTypeRaw === "string" ? partitionTypeRaw : "range";
|
|
394
|
-
const isIntegerBased = validNumericPattern.test(validatedRetention) ||
|
|
395
|
-
partitionType.toLowerCase() === "native" ||
|
|
396
|
-
partitionType.toLowerCase().includes("id");
|
|
397
|
-
// Use "below" for integer-based, "older than" for time-based partitions
|
|
398
|
-
const retentionPhrase = isIntegerBased
|
|
399
|
-
? `partitions with values below ${validatedRetention}`
|
|
400
|
-
: `partitions older than ${validatedRetention}`;
|
|
401
|
-
return {
|
|
402
|
-
success: true,
|
|
403
|
-
parentTable: validatedParentTable,
|
|
404
|
-
retention: validatedRetention,
|
|
405
|
-
retentionKeepTable: retentionKeepTable ?? false,
|
|
406
|
-
message: `Retention policy set: ${retentionPhrase} will be ${retentionKeepTable === true ? "detached" : "dropped"}`,
|
|
407
|
-
};
|
|
408
|
-
},
|
|
409
|
-
};
|
|
410
|
-
}
|
|
411
|
-
/**
|
|
412
|
-
* Undo partitioning - convert back to regular table
|
|
413
|
-
*/
|
|
414
|
-
export function createPartmanUndoPartitionTool(adapter) {
|
|
415
|
-
return {
|
|
416
|
-
name: "pg_partman_undo_partition",
|
|
417
|
-
description: `Convert a partitioned table back to a regular table by moving all data from child partitions to a TARGET table.
|
|
418
|
-
|
|
419
|
-
IMPORTANT: The targetTable parameter is REQUIRED. pg_partman does not consolidate data back to the parent table directly.
|
|
420
|
-
You must first create an empty table with the same structure as the parent, then specify it as targetTable.
|
|
421
|
-
|
|
422
|
-
Example: undoPartition({ parentTable: "public.events", targetTable: "public.events_consolidated" })`,
|
|
423
|
-
group: "partman",
|
|
424
|
-
inputSchema: PartmanUndoPartitionSchemaBase,
|
|
425
|
-
outputSchema: PartmanUndoPartitionOutputSchema,
|
|
426
|
-
annotations: destructive("Undo Partitioning"),
|
|
427
|
-
icons: getToolIcons("partman", destructive("Undo Partitioning")),
|
|
428
|
-
handler: async (params, _context) => {
|
|
429
|
-
const { parentTable, targetTable, batchSize, keepTable } = PartmanUndoPartitionSchema.parse(params);
|
|
430
|
-
// Validate required parameters with clear error messages
|
|
431
|
-
if (!parentTable || !targetTable) {
|
|
432
|
-
const missing = [];
|
|
433
|
-
if (!parentTable)
|
|
434
|
-
missing.push("parentTable");
|
|
435
|
-
if (!targetTable)
|
|
436
|
-
missing.push("targetTable (or target)");
|
|
437
|
-
return {
|
|
438
|
-
success: false,
|
|
439
|
-
error: `Missing required parameters: ${missing.join(", ")}.`,
|
|
440
|
-
hint: 'Example: pg_partman_undo_partition({ parentTable: "public.events", targetTable: "public.events_archive" }). Target table must exist first.',
|
|
441
|
-
aliases: { target: "targetTable" },
|
|
442
|
-
};
|
|
443
|
-
}
|
|
444
|
-
// At this point, parentTable and targetTable are guaranteed to be defined
|
|
445
|
-
// Auto-prefix 'public.' schema when not specified (consistent with parentTable behavior)
|
|
446
|
-
const validatedParentTable = parentTable.includes(".")
|
|
447
|
-
? parentTable
|
|
448
|
-
: `public.${parentTable}`;
|
|
449
|
-
const validatedTargetTable = targetTable.includes(".")
|
|
450
|
-
? targetTable
|
|
451
|
-
: `public.${targetTable}`;
|
|
452
|
-
// Pre-validate: Check that target table exists before calling pg_partman
|
|
453
|
-
const partmanSchema = await getPartmanSchema(adapter);
|
|
454
|
-
// Parse target table name to check existence
|
|
455
|
-
const [targetSchema, targetTableName] = [
|
|
456
|
-
validatedTargetTable.split(".")[0],
|
|
457
|
-
validatedTargetTable.split(".")[1],
|
|
458
|
-
];
|
|
459
|
-
const tableExistsResult = await adapter.executeQuery(`
|
|
460
|
-
SELECT 1 FROM information_schema.tables
|
|
461
|
-
WHERE table_schema = $1 AND table_name = $2
|
|
462
|
-
`, [targetSchema, targetTableName]);
|
|
463
|
-
if ((tableExistsResult.rows?.length ?? 0) === 0) {
|
|
464
|
-
return {
|
|
465
|
-
success: false,
|
|
466
|
-
error: `Target table '${validatedTargetTable}' does not exist.`,
|
|
467
|
-
hint: "pg_partman's undo_partition requires the target table to exist before consolidating data. " +
|
|
468
|
-
"Create the target table first with the same structure as the parent table.",
|
|
469
|
-
};
|
|
470
|
-
}
|
|
471
|
-
const args = [
|
|
472
|
-
`p_parent_table := '${validatedParentTable}'`,
|
|
473
|
-
`p_target_table := '${validatedTargetTable}'`,
|
|
474
|
-
];
|
|
475
|
-
if (batchSize !== undefined) {
|
|
476
|
-
args.push(`p_loop_count := ${String(batchSize)}`);
|
|
477
|
-
}
|
|
478
|
-
if (keepTable !== undefined) {
|
|
479
|
-
args.push(`p_keep_table := ${String(keepTable)}`);
|
|
480
|
-
}
|
|
481
|
-
// undo_partition_proc is a PROCEDURE, not a function - use CALL syntax
|
|
482
|
-
// Uses callPartmanProcedure to set search_path, resolving hardcoded
|
|
483
|
-
// 'partman.*' references inside pg_partman's internal functions
|
|
484
|
-
const sql = `CALL ${partmanSchema}.undo_partition_proc(${args.join(", ")})`;
|
|
485
|
-
try {
|
|
486
|
-
await callPartmanProcedure(adapter, partmanSchema, sql);
|
|
487
|
-
}
|
|
488
|
-
catch (error) {
|
|
489
|
-
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
490
|
-
const firstLine = errorMsg.split("\n")[0] ?? errorMsg;
|
|
491
|
-
return {
|
|
492
|
-
success: false,
|
|
493
|
-
parentTable: validatedParentTable,
|
|
494
|
-
targetTable: validatedTargetTable,
|
|
495
|
-
error: firstLine.includes("No entry in part_config")
|
|
496
|
-
? `No pg_partman configuration found for '${validatedParentTable}'.`
|
|
497
|
-
: `Failed to undo partition: ${firstLine}`,
|
|
498
|
-
hint: "Use pg_partman_show_config to verify the partition set exists and is properly configured.",
|
|
499
|
-
};
|
|
500
|
-
}
|
|
501
|
-
// Note: pg_partman's undo_partition detaches child partitions but leaves them as standalone tables
|
|
502
|
-
// This allows data recovery if needed, but users should clean up manually
|
|
503
|
-
const keepTableValue = keepTable ?? true;
|
|
504
|
-
return {
|
|
505
|
-
success: true,
|
|
506
|
-
parentTable: validatedParentTable,
|
|
507
|
-
targetTable: validatedTargetTable,
|
|
508
|
-
message: `Partition set removed for ${validatedParentTable}. Data consolidated to ${validatedTargetTable}.`,
|
|
509
|
-
note: keepTableValue
|
|
510
|
-
? "The parent table and detached child partitions still exist. " +
|
|
511
|
-
`To clean up: DROP TABLE ${validatedParentTable} CASCADE;`
|
|
512
|
-
: `The parent table still exists. To clean up: DROP TABLE ${validatedParentTable} CASCADE;`,
|
|
513
|
-
};
|
|
514
|
-
},
|
|
515
|
-
};
|
|
516
|
-
}
|
|
517
|
-
/**
|
|
518
|
-
* Analyze partition health and provide recommendations
|
|
519
|
-
*/
|
|
520
|
-
export function createPartmanAnalyzeHealthTool(adapter) {
|
|
521
|
-
return {
|
|
522
|
-
name: "pg_partman_analyze_partition_health",
|
|
523
|
-
description: `Analyze the health of partition sets managed by pg_partman.
|
|
524
|
-
Checks for issues like data in default partitions, missing premake partitions,
|
|
525
|
-
stale maintenance, and retention configuration.`,
|
|
526
|
-
group: "partman",
|
|
527
|
-
inputSchema: z
|
|
528
|
-
.preprocess((input) => {
|
|
529
|
-
if (typeof input !== "object" || input === null)
|
|
530
|
-
return input;
|
|
531
|
-
const raw = input;
|
|
532
|
-
const result = { ...raw };
|
|
533
|
-
// Alias: table → parentTable
|
|
534
|
-
if (result.table && !result.parentTable) {
|
|
535
|
-
result.parentTable = result.table;
|
|
536
|
-
}
|
|
537
|
-
// Auto-prefix public. for parentTable when no schema specified
|
|
538
|
-
if (result.parentTable && !result.parentTable.includes(".")) {
|
|
539
|
-
result.parentTable = `public.${result.parentTable}`;
|
|
540
|
-
}
|
|
541
|
-
return result;
|
|
542
|
-
}, z.object({
|
|
543
|
-
parentTable: z
|
|
544
|
-
.string()
|
|
545
|
-
.optional()
|
|
546
|
-
.describe("Specific parent table to analyze (all if omitted)"),
|
|
547
|
-
limit: z
|
|
548
|
-
.number()
|
|
549
|
-
.optional()
|
|
550
|
-
.describe("Maximum number of partition sets to analyze (default: 50, use 0 for all)"),
|
|
551
|
-
}))
|
|
552
|
-
.default({}),
|
|
553
|
-
outputSchema: PartmanAnalyzeHealthOutputSchema,
|
|
554
|
-
annotations: readOnly("Analyze Partition Health"),
|
|
555
|
-
icons: getToolIcons("partman", readOnly("Analyze Partition Health")),
|
|
556
|
-
handler: async (params, _context) => {
|
|
557
|
-
const AnalyzeHealthSchema = z
|
|
558
|
-
.preprocess((input) => {
|
|
559
|
-
if (typeof input !== "object" || input === null)
|
|
560
|
-
return input;
|
|
561
|
-
const raw = input;
|
|
562
|
-
const result = { ...raw };
|
|
563
|
-
// Alias: table → parentTable
|
|
564
|
-
if (result.table && !result.parentTable) {
|
|
565
|
-
result.parentTable = result.table;
|
|
177
|
+
const args = [`p_parent_table := '${parentTable}'`];
|
|
178
|
+
if (batchSize !== undefined && !isNaN(batchSize)) {
|
|
179
|
+
args.push(`p_loop_count := ${String(batchSize)}`);
|
|
566
180
|
}
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
result.parentTable = `public.${result.parentTable}`;
|
|
181
|
+
if (lockWaitSeconds !== undefined && !isNaN(lockWaitSeconds)) {
|
|
182
|
+
args.push(`p_lock_wait := ${String(lockWaitSeconds)}`);
|
|
570
183
|
}
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
.default({});
|
|
577
|
-
const parsed = AnalyzeHealthSchema.parse(params ?? {});
|
|
578
|
-
const queryParams = [];
|
|
579
|
-
const partmanSchema = await getPartmanSchema(adapter);
|
|
580
|
-
// Get total count first for pagination
|
|
581
|
-
let countSql = `SELECT COUNT(*) as total FROM ${partmanSchema}.part_config`;
|
|
582
|
-
const countParams = [];
|
|
583
|
-
if (parsed.parentTable !== undefined) {
|
|
584
|
-
countSql += " WHERE parent_table = $1";
|
|
585
|
-
countParams.push(parsed.parentTable);
|
|
586
|
-
}
|
|
587
|
-
const countResult = await adapter.executeQuery(countSql, countParams);
|
|
588
|
-
const totalCount = Number(countResult.rows?.[0]?.["total"] ?? 0);
|
|
589
|
-
// Apply limit (default 50, 0 means no limit)
|
|
590
|
-
const limit = parsed.limit ?? 50;
|
|
591
|
-
const applyLimit = limit > 0;
|
|
592
|
-
let configSql = `
|
|
593
|
-
SELECT
|
|
594
|
-
parent_table,
|
|
595
|
-
control,
|
|
596
|
-
partition_interval,
|
|
597
|
-
premake,
|
|
598
|
-
retention,
|
|
599
|
-
retention_keep_table,
|
|
600
|
-
automatic_maintenance,
|
|
601
|
-
template_table
|
|
184
|
+
const partmanSchema = await getPartmanSchema(adapter);
|
|
185
|
+
let configResult;
|
|
186
|
+
try {
|
|
187
|
+
configResult = await adapter.executeQuery(`
|
|
188
|
+
SELECT control, epoch
|
|
602
189
|
FROM ${partmanSchema}.part_config
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
const parentTable = config["parent_table"];
|
|
627
|
-
const issues = [];
|
|
628
|
-
const warnings = [];
|
|
629
|
-
const recommendations = [];
|
|
630
|
-
// Check if parent table still exists (handle orphaned configs)
|
|
631
|
-
const [tableSchema, tableName] = parentTable.includes(".")
|
|
632
|
-
? [parentTable.split(".")[0], parentTable.split(".")[1]]
|
|
190
|
+
WHERE parent_table = $1
|
|
191
|
+
`, [parentTable]);
|
|
192
|
+
}
|
|
193
|
+
catch {
|
|
194
|
+
return {
|
|
195
|
+
success: false,
|
|
196
|
+
error: "pg_partman extension not found or not properly installed.",
|
|
197
|
+
hint: "Install pg_partman with pg_partman_create_extension, then configure the partition set with pg_partman_create_parent.",
|
|
198
|
+
};
|
|
199
|
+
}
|
|
200
|
+
const config = configResult.rows?.[0];
|
|
201
|
+
if (!config) {
|
|
202
|
+
return {
|
|
203
|
+
success: false,
|
|
204
|
+
error: `No pg_partman configuration found for ${parentTable}`,
|
|
205
|
+
};
|
|
206
|
+
}
|
|
207
|
+
// Get row count in default partition before moving data
|
|
208
|
+
const [partSchema, partTableName] = parentTable.includes(".")
|
|
209
|
+
? [
|
|
210
|
+
parentTable.split(".")[0] ?? "public",
|
|
211
|
+
parentTable.split(".")[1] ?? parentTable,
|
|
212
|
+
]
|
|
633
213
|
: ["public", parentTable];
|
|
634
|
-
const
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
issues: ["Orphaned configuration - parent table no longer exists"],
|
|
643
|
-
warnings: [],
|
|
644
|
-
recommendations: [
|
|
645
|
-
"Remove orphaned config from part_config table or recreate the table",
|
|
646
|
-
],
|
|
647
|
-
partitionCount: 0,
|
|
648
|
-
hasDefaultPartition: false,
|
|
649
|
-
hasDataInDefault: false,
|
|
650
|
-
});
|
|
651
|
-
continue;
|
|
214
|
+
const defaultPartitionName = `${partSchema}.${partTableName}_default`;
|
|
215
|
+
let rowsBeforeMove = 0;
|
|
216
|
+
try {
|
|
217
|
+
const beforeResult = await adapter.executeQuery(`SELECT COUNT(*)::int as count FROM ${defaultPartitionName}`);
|
|
218
|
+
rowsBeforeMove = Number(beforeResult.rows?.[0]?.["count"] ?? 0);
|
|
219
|
+
}
|
|
220
|
+
catch {
|
|
221
|
+
// Default partition might not exist - that's okay
|
|
652
222
|
}
|
|
653
|
-
|
|
223
|
+
// partition_data_proc is a PROCEDURE, not a function - use CALL syntax
|
|
224
|
+
// Uses callPartmanProcedure to set search_path, resolving hardcoded
|
|
225
|
+
// 'partman.*' references inside pg_partman's internal functions
|
|
226
|
+
const sql = `CALL ${partmanSchema}.partition_data_proc(${args.join(", ")})`;
|
|
654
227
|
try {
|
|
655
|
-
|
|
656
|
-
SELECT COUNT(*) as count
|
|
657
|
-
FROM ${partmanSchema}.show_partitions(p_parent_table := $1)
|
|
658
|
-
`, [parentTable]);
|
|
659
|
-
partitionCount = Number(partCountResult.rows?.[0]?.["count"] ?? 0);
|
|
228
|
+
await callPartmanProcedure(adapter, partmanSchema, sql);
|
|
660
229
|
}
|
|
661
230
|
catch (e) {
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
231
|
+
const errorMsg = e instanceof Error ? e.message : String(e);
|
|
232
|
+
return {
|
|
233
|
+
success: false,
|
|
665
234
|
parentTable,
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
"Verify pg_partman configuration with pg_partman_show_config",
|
|
671
|
-
"If table was dropped, remove orphaned config from part_config",
|
|
672
|
-
],
|
|
673
|
-
partitionCount: 0,
|
|
674
|
-
hasDefaultPartition: false,
|
|
675
|
-
hasDataInDefault: false,
|
|
676
|
-
});
|
|
677
|
-
continue;
|
|
678
|
-
}
|
|
679
|
-
const premake = config["premake"] ?? 4;
|
|
680
|
-
if (partitionCount < premake) {
|
|
681
|
-
warnings.push(`Only ${String(partitionCount)} partitions exist, premake is set to ${String(premake)}`);
|
|
682
|
-
recommendations.push("Run pg_partman_run_maintenance to create premake partitions");
|
|
683
|
-
}
|
|
684
|
-
// Check if default partition exists
|
|
685
|
-
const defaultCheckResult = await adapter.executeQuery(`
|
|
686
|
-
SELECT c.relname as default_partition, pn.nspname as default_schema
|
|
687
|
-
FROM pg_inherits i
|
|
688
|
-
JOIN pg_class c ON c.oid = i.inhrelid
|
|
689
|
-
JOIN pg_class p ON p.oid = i.inhparent
|
|
690
|
-
JOIN pg_namespace pn ON pn.oid = p.relnamespace
|
|
691
|
-
WHERE (pn.nspname || '.' || p.relname) = $1
|
|
692
|
-
AND c.relname LIKE '%_default'
|
|
693
|
-
`, [parentTable]);
|
|
694
|
-
const hasDefaultPartition = (defaultCheckResult.rows?.length ?? 0) > 0;
|
|
695
|
-
let hasDataInDefault = false;
|
|
696
|
-
// Use actual COUNT(*) instead of reltuples estimate — reltuples
|
|
697
|
-
// returns 0 or -1 for recently-inserted data before ANALYZE runs
|
|
698
|
-
if (hasDefaultPartition) {
|
|
699
|
-
const defSchema = defaultCheckResult.rows?.[0]?.["default_schema"];
|
|
700
|
-
const defTable = defaultCheckResult.rows?.[0]?.["default_partition"];
|
|
701
|
-
try {
|
|
702
|
-
const countResult = await adapter.executeQuery(`SELECT COUNT(*) as count FROM (SELECT 1 FROM ${defSchema}.${defTable} LIMIT 1) t`);
|
|
703
|
-
hasDataInDefault =
|
|
704
|
-
Number(countResult.rows?.[0]?.["count"] ?? 0) > 0;
|
|
705
|
-
}
|
|
706
|
-
catch {
|
|
707
|
-
// Default partition might not be accessible
|
|
708
|
-
}
|
|
235
|
+
error: `Failed to move data from default partition: ${errorMsg.split("\n")[0] ?? errorMsg}`,
|
|
236
|
+
hint: "Ensure pg_partman is properly installed and the partition set is configured correctly. " +
|
|
237
|
+
"Use pg_partman_show_config to verify configuration.",
|
|
238
|
+
};
|
|
709
239
|
}
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
|
|
240
|
+
// Get row count in default partition after moving data
|
|
241
|
+
let rowsAfterMove = 0;
|
|
242
|
+
try {
|
|
243
|
+
const afterResult = await adapter.executeQuery(`SELECT COUNT(*)::int as count FROM ${defaultPartitionName}`);
|
|
244
|
+
rowsAfterMove = Number(afterResult.rows?.[0]?.["count"] ?? 0);
|
|
713
245
|
}
|
|
714
|
-
|
|
715
|
-
|
|
716
|
-
const autoMaint = config["automatic_maintenance"];
|
|
717
|
-
if (autoMaint !== "on") {
|
|
718
|
-
warnings.push("Automatic maintenance is not enabled");
|
|
719
|
-
recommendations.push("Schedule regular maintenance with pg_cron or enable automatic_maintenance");
|
|
246
|
+
catch {
|
|
247
|
+
// Default partition might not exist
|
|
720
248
|
}
|
|
721
|
-
|
|
249
|
+
const rowsMoved = rowsBeforeMove - rowsAfterMove;
|
|
250
|
+
return {
|
|
251
|
+
success: true,
|
|
722
252
|
parentTable,
|
|
723
|
-
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
253
|
+
rowsMoved: rowsMoved > 0 ? rowsMoved : 0,
|
|
254
|
+
rowsRemaining: rowsAfterMove,
|
|
255
|
+
message: rowsMoved > 0
|
|
256
|
+
? `Data partitioning completed - ${String(rowsMoved)} rows moved from default to child partitions`
|
|
257
|
+
: "Data partitioning completed - no rows needed to be moved (default partition empty or already partitioned)",
|
|
258
|
+
};
|
|
259
|
+
}
|
|
260
|
+
catch (error) {
|
|
261
|
+
return {
|
|
262
|
+
success: false,
|
|
263
|
+
error: formatPostgresError(error, {
|
|
264
|
+
tool: "pg_partman_partition_data",
|
|
265
|
+
}),
|
|
266
|
+
};
|
|
730
267
|
}
|
|
731
|
-
const totalIssues = healthChecks.reduce((sum, h) => sum + h.issues.length, 0);
|
|
732
|
-
const totalWarnings = healthChecks.reduce((sum, h) => sum + h.warnings.length, 0);
|
|
733
|
-
const truncated = applyLimit && totalCount > limit;
|
|
734
|
-
return {
|
|
735
|
-
partitionSets: healthChecks,
|
|
736
|
-
truncated,
|
|
737
|
-
totalCount,
|
|
738
|
-
summary: {
|
|
739
|
-
totalPartitionSets: truncated ? totalCount : healthChecks.length,
|
|
740
|
-
totalIssues,
|
|
741
|
-
totalWarnings,
|
|
742
|
-
overallHealth: totalIssues === 0
|
|
743
|
-
? totalWarnings === 0
|
|
744
|
-
? "healthy"
|
|
745
|
-
: "warnings"
|
|
746
|
-
: "issues_found",
|
|
747
|
-
},
|
|
748
|
-
};
|
|
749
268
|
},
|
|
750
269
|
};
|
|
751
270
|
}
|