directus 9.23.1 → 9.23.4
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/dist/app.js +25 -21
- package/dist/auth/auth.d.ts +3 -3
- package/dist/auth/auth.js +2 -0
- package/dist/auth/drivers/ldap.d.ts +1 -1
- package/dist/auth/drivers/ldap.js +57 -46
- package/dist/auth/drivers/local.d.ts +1 -1
- package/dist/auth/drivers/local.js +20 -17
- package/dist/auth/drivers/oauth2.d.ts +1 -1
- package/dist/auth/drivers/oauth2.js +44 -35
- package/dist/auth/drivers/openid.d.ts +1 -1
- package/dist/auth/drivers/openid.js +50 -41
- package/dist/auth/drivers/saml.d.ts +1 -1
- package/dist/auth/drivers/saml.js +20 -17
- package/dist/auth.d.ts +1 -1
- package/dist/auth.js +8 -7
- package/dist/cache.d.ts +9 -1
- package/dist/cache.js +66 -18
- package/dist/cli/commands/bootstrap/index.js +7 -6
- package/dist/cli/commands/init/index.js +3 -3
- package/dist/cli/commands/schema/apply.js +14 -15
- package/dist/cli/commands/schema/snapshot.js +2 -2
- package/dist/cli/utils/create-db-connection.d.ts +1 -1
- package/dist/cli/utils/create-db-connection.js +3 -2
- package/dist/cli/utils/create-env/index.d.ts +2 -2
- package/dist/cli/utils/create-env/index.js +1 -1
- package/dist/cli/utils/drivers.d.ts +1 -1
- package/dist/constants.d.ts +3 -2
- package/dist/constants.js +7 -7
- package/dist/controllers/activity.js +10 -11
- package/dist/controllers/assets.js +31 -25
- package/dist/controllers/auth.js +40 -26
- package/dist/controllers/collections.js +10 -10
- package/dist/controllers/dashboards.js +14 -11
- package/dist/controllers/extensions.js +3 -3
- package/dist/controllers/fields.js +20 -20
- package/dist/controllers/files.js +26 -20
- package/dist/controllers/flows.js +16 -13
- package/dist/controllers/folders.js +14 -11
- package/dist/controllers/graphql.js +6 -8
- package/dist/controllers/items.js +22 -19
- package/dist/controllers/not-found.d.ts +1 -1
- package/dist/controllers/not-found.js +1 -2
- package/dist/controllers/notifications.js +14 -11
- package/dist/controllers/operations.js +14 -11
- package/dist/controllers/panels.js +14 -11
- package/dist/controllers/permissions.js +14 -11
- package/dist/controllers/presets.js +14 -11
- package/dist/controllers/relations.js +10 -10
- package/dist/controllers/revisions.js +3 -3
- package/dist/controllers/roles.js +14 -11
- package/dist/controllers/schema.js +5 -5
- package/dist/controllers/server.js +7 -7
- package/dist/controllers/settings.js +2 -2
- package/dist/controllers/shares.js +21 -18
- package/dist/controllers/users.js +32 -36
- package/dist/controllers/utils.js +10 -15
- package/dist/controllers/webhooks.js +14 -11
- package/dist/database/helpers/fn/dialects/mssql.d.ts +1 -1
- package/dist/database/helpers/fn/dialects/mssql.js +10 -11
- package/dist/database/helpers/fn/dialects/mysql.d.ts +1 -1
- package/dist/database/helpers/fn/dialects/mysql.js +2 -3
- package/dist/database/helpers/fn/dialects/oracle.d.ts +1 -1
- package/dist/database/helpers/fn/dialects/oracle.js +10 -11
- package/dist/database/helpers/fn/dialects/postgres.d.ts +1 -1
- package/dist/database/helpers/fn/dialects/postgres.js +10 -11
- package/dist/database/helpers/fn/dialects/sqlite.d.ts +1 -1
- package/dist/database/helpers/fn/dialects/sqlite.js +10 -11
- package/dist/database/helpers/fn/types.d.ts +5 -6
- package/dist/database/helpers/fn/types.js +4 -5
- package/dist/database/helpers/geometry/dialects/mssql.d.ts +3 -3
- package/dist/database/helpers/geometry/dialects/mysql.d.ts +1 -1
- package/dist/database/helpers/geometry/dialects/oracle.d.ts +3 -3
- package/dist/database/helpers/geometry/dialects/postgres.d.ts +3 -3
- package/dist/database/helpers/geometry/dialects/postgres.js +1 -2
- package/dist/database/helpers/geometry/dialects/redshift.d.ts +2 -2
- package/dist/database/helpers/geometry/dialects/sqlite.d.ts +1 -1
- package/dist/database/helpers/geometry/types.d.ts +2 -2
- package/dist/database/helpers/geometry/types.js +1 -2
- package/dist/database/helpers/index.d.ts +5 -5
- package/dist/database/helpers/schema/dialects/cockroachdb.d.ts +1 -1
- package/dist/database/helpers/schema/dialects/mssql.d.ts +1 -1
- package/dist/database/helpers/schema/dialects/mysql.d.ts +1 -1
- package/dist/database/helpers/schema/dialects/mysql.js +1 -2
- package/dist/database/helpers/schema/dialects/oracle.d.ts +2 -2
- package/dist/database/helpers/schema/dialects/oracle.js +4 -6
- package/dist/database/helpers/schema/types.d.ts +4 -4
- package/dist/database/helpers/types.d.ts +1 -1
- package/dist/database/helpers/types.js +1 -0
- package/dist/database/index.d.ts +1 -1
- package/dist/database/index.js +13 -13
- package/dist/database/migrations/20201028A-remove-collection-foreign-keys.d.ts +1 -1
- package/dist/database/migrations/20201029A-remove-system-relations.d.ts +1 -1
- package/dist/database/migrations/20201029B-remove-system-collections.d.ts +1 -1
- package/dist/database/migrations/20201029C-remove-system-fields.d.ts +1 -1
- package/dist/database/migrations/20201105A-add-cascade-system-relations.d.ts +1 -1
- package/dist/database/migrations/20201105B-change-webhook-url-type.d.ts +1 -1
- package/dist/database/migrations/20210225A-add-relations-sort-field.d.ts +1 -1
- package/dist/database/migrations/20210225A-add-relations-sort-field.js +1 -2
- package/dist/database/migrations/20210304A-remove-locked-fields.d.ts +1 -1
- package/dist/database/migrations/20210312A-webhooks-collections-text.d.ts +1 -1
- package/dist/database/migrations/20210331A-add-refresh-interval.d.ts +1 -1
- package/dist/database/migrations/20210415A-make-filesize-nullable.d.ts +1 -1
- package/dist/database/migrations/20210416A-add-collections-accountability.d.ts +1 -1
- package/dist/database/migrations/20210422A-remove-files-interface.d.ts +1 -1
- package/dist/database/migrations/20210506A-rename-interfaces.d.ts +1 -1
- package/dist/database/migrations/20210510A-restructure-relations.d.ts +1 -1
- package/dist/database/migrations/20210518A-add-foreign-key-constraints.d.ts +1 -1
- package/dist/database/migrations/20210518A-add-foreign-key-constraints.js +1 -1
- package/dist/database/migrations/20210519A-add-system-fk-triggers.d.ts +1 -1
- package/dist/database/migrations/20210519A-add-system-fk-triggers.js +2 -2
- package/dist/database/migrations/20210521A-add-collections-icon-color.d.ts +1 -1
- package/dist/database/migrations/20210525A-add-insights.d.ts +1 -1
- package/dist/database/migrations/20210608A-add-deep-clone-config.d.ts +1 -1
- package/dist/database/migrations/20210626A-change-filesize-bigint.d.ts +1 -1
- package/dist/database/migrations/20210716A-add-conditions-to-fields.d.ts +1 -1
- package/dist/database/migrations/20210721A-add-default-folder.d.ts +1 -1
- package/dist/database/migrations/20210802A-replace-groups.d.ts +1 -1
- package/dist/database/migrations/20210803A-add-required-to-fields.d.ts +1 -1
- package/dist/database/migrations/20210805A-update-groups.d.ts +1 -1
- package/dist/database/migrations/20210805B-change-image-metadata-structure.d.ts +1 -1
- package/dist/database/migrations/20210805B-change-image-metadata-structure.js +15 -15
- package/dist/database/migrations/20210811A-add-geometry-config.d.ts +1 -1
- package/dist/database/migrations/20210831A-remove-limit-column.d.ts +1 -1
- package/dist/database/migrations/20210903A-add-auth-provider.d.ts +1 -1
- package/dist/database/migrations/20210907A-webhooks-collections-not-null.d.ts +1 -1
- package/dist/database/migrations/20210910A-move-module-setup.d.ts +1 -1
- package/dist/database/migrations/20210920A-webhooks-url-not-null.d.ts +1 -1
- package/dist/database/migrations/20210924A-add-collection-organization.d.ts +1 -1
- package/dist/database/migrations/20210927A-replace-fields-group.d.ts +1 -1
- package/dist/database/migrations/20210927B-replace-m2m-interface.d.ts +1 -1
- package/dist/database/migrations/20210929A-rename-login-action.d.ts +1 -1
- package/dist/database/migrations/20211007A-update-presets.d.ts +1 -1
- package/dist/database/migrations/20211007A-update-presets.js +7 -9
- package/dist/database/migrations/20211009A-add-auth-data.d.ts +1 -1
- package/dist/database/migrations/20211016A-add-webhook-headers.d.ts +1 -1
- package/dist/database/migrations/20211103A-set-unique-to-user-token.d.ts +1 -1
- package/dist/database/migrations/20211103B-update-special-geometry.d.ts +1 -1
- package/dist/database/migrations/20211104A-remove-collections-listing.d.ts +1 -1
- package/dist/database/migrations/20211118A-add-notifications.d.ts +1 -1
- package/dist/database/migrations/20211211A-add-shares.d.ts +1 -1
- package/dist/database/migrations/20211230A-add-project-descriptor.d.ts +1 -1
- package/dist/database/migrations/20220303A-remove-default-project-color.d.ts +1 -1
- package/dist/database/migrations/20220308A-add-bookmark-icon-and-color.d.ts +1 -1
- package/dist/database/migrations/20220314A-add-translation-strings.d.ts +1 -1
- package/dist/database/migrations/20220322A-rename-field-typecast-flags.d.ts +1 -1
- package/dist/database/migrations/20220323A-add-field-validation.d.ts +1 -1
- package/dist/database/migrations/20220325A-fix-typecast-flags.d.ts +1 -1
- package/dist/database/migrations/20220325B-add-default-language.d.ts +1 -1
- package/dist/database/migrations/20220402A-remove-default-value-panel-icon.d.ts +1 -1
- package/dist/database/migrations/20220429A-add-flows.d.ts +1 -1
- package/dist/database/migrations/20220429B-add-color-to-insights-icon.d.ts +1 -1
- package/dist/database/migrations/20220429C-drop-non-null-from-ip-of-activity.d.ts +1 -1
- package/dist/database/migrations/20220429D-drop-non-null-from-sender-of-notifications.d.ts +1 -1
- package/dist/database/migrations/20220614A-rename-hook-trigger-to-event.d.ts +1 -1
- package/dist/database/migrations/20220801A-update-notifications-timestamp-column.d.ts +1 -1
- package/dist/database/migrations/20220802A-add-custom-aspect-ratios.d.ts +1 -1
- package/dist/database/migrations/20220826A-add-origin-to-accountability.d.ts +1 -1
- package/dist/database/migrations/run.d.ts +1 -1
- package/dist/database/migrations/run.js +1 -1
- package/dist/database/run-ast.d.ts +3 -3
- package/dist/database/run-ast.js +21 -30
- package/dist/database/seeds/run.d.ts +1 -1
- package/dist/database/seeds/run.js +1 -2
- package/dist/database/system-data/app-access-permissions/index.d.ts +1 -1
- package/dist/database/system-data/collections/index.d.ts +1 -1
- package/dist/database/system-data/collections/index.js +2 -2
- package/dist/database/system-data/fields/collections.yaml +2 -0
- package/dist/database/system-data/fields/index.d.ts +1 -1
- package/dist/database/system-data/fields/index.js +3 -4
- package/dist/database/system-data/fields/settings.yaml +4 -0
- package/dist/database/system-data/relations/index.d.ts +1 -1
- package/dist/emitter.d.ts +1 -1
- package/dist/emitter.js +3 -0
- package/dist/env.js +11 -3
- package/dist/exceptions/database/dialects/mssql.d.ts +1 -1
- package/dist/exceptions/database/dialects/mssql.js +5 -6
- package/dist/exceptions/database/dialects/mysql.d.ts +1 -1
- package/dist/exceptions/database/dialects/mysql.js +19 -25
- package/dist/exceptions/database/dialects/oracle.d.ts +1 -1
- package/dist/exceptions/database/dialects/postgres.d.ts +1 -1
- package/dist/exceptions/database/dialects/sqlite.d.ts +1 -1
- package/dist/exceptions/database/translate.d.ts +1 -1
- package/dist/exceptions/database/value-out-of-range.js +1 -1
- package/dist/exceptions/range-not-satisfiable.js +2 -3
- package/dist/extensions.d.ts +1 -1
- package/dist/extensions.js +43 -33
- package/dist/flows.js +65 -46
- package/dist/logger.d.ts +2 -1
- package/dist/logger.js +35 -19
- package/dist/logger.test.d.ts +1 -0
- package/dist/mailer.js +16 -16
- package/dist/messenger.js +9 -7
- package/dist/middleware/authenticate.d.ts +1 -1
- package/dist/middleware/authenticate.js +13 -6
- package/dist/middleware/cache.d.ts +1 -1
- package/dist/middleware/cache.js +16 -16
- package/dist/middleware/check-ip.d.ts +1 -1
- package/dist/middleware/check-ip.js +1 -1
- package/dist/middleware/collection-exists.d.ts +1 -1
- package/dist/middleware/collection-exists.js +5 -5
- package/dist/middleware/cors.d.ts +1 -1
- package/dist/middleware/cors.js +7 -7
- package/dist/middleware/error-handler.d.ts +1 -1
- package/dist/middleware/error-handler.js +11 -12
- package/dist/middleware/extract-token.d.ts +1 -1
- package/dist/middleware/extract-token.js +2 -2
- package/dist/middleware/get-permissions.d.ts +1 -1
- package/dist/middleware/graphql.d.ts +1 -1
- package/dist/middleware/graphql.js +15 -9
- package/dist/middleware/rate-limiter-global.d.ts +5 -0
- package/dist/middleware/rate-limiter-global.js +48 -0
- package/dist/middleware/{rate-limiter.d.ts → rate-limiter-ip.d.ts} +2 -2
- package/dist/middleware/{rate-limiter.js → rate-limiter-ip.js} +5 -5
- package/dist/middleware/respond.d.ts +1 -1
- package/dist/middleware/respond.js +18 -19
- package/dist/middleware/sanitize-query.d.ts +1 -1
- package/dist/middleware/sanitize-query.js +1 -1
- package/dist/middleware/schema.d.ts +1 -1
- package/dist/middleware/use-collection.d.ts +1 -1
- package/dist/operations/condition/index.d.ts +1 -1
- package/dist/operations/exec/index.js +15 -4
- package/dist/operations/item-create/index.js +1 -2
- package/dist/operations/item-delete/index.d.ts +1 -1
- package/dist/operations/item-read/index.d.ts +1 -1
- package/dist/operations/item-update/index.d.ts +1 -1
- package/dist/operations/item-update/index.js +1 -2
- package/dist/operations/notification/index.js +1 -2
- package/dist/operations/request/index.js +19 -19
- package/dist/operations/trigger/index.js +2 -3
- package/dist/rate-limiter.d.ts +1 -1
- package/dist/rate-limiter.js +9 -9
- package/dist/request/validate-ip.js +2 -2
- package/dist/server.js +12 -13
- package/dist/services/activity.d.ts +1 -1
- package/dist/services/activity.js +17 -16
- package/dist/services/assets.d.ts +3 -3
- package/dist/services/assets.js +35 -37
- package/dist/services/authentication.d.ts +2 -2
- package/dist/services/authentication.js +22 -19
- package/dist/services/authorization.d.ts +3 -3
- package/dist/services/authorization.js +27 -31
- package/dist/services/collections.d.ts +5 -5
- package/dist/services/collections.js +54 -50
- package/dist/services/dashboards.d.ts +1 -1
- package/dist/services/fields.d.ts +5 -5
- package/dist/services/fields.js +50 -50
- package/dist/services/files.d.ts +1 -2
- package/dist/services/files.js +33 -27
- package/dist/services/flows.d.ts +2 -2
- package/dist/services/folders.d.ts +1 -1
- package/dist/services/graphql/index.d.ts +4 -4
- package/dist/services/graphql/index.js +259 -252
- package/dist/services/graphql/utils/add-path-to-validation-error.js +1 -2
- package/dist/services/graphql/utils/process-error.d.ts +2 -2
- package/dist/services/graphql/utils/process-error.js +11 -4
- package/dist/services/import-export.d.ts +3 -3
- package/dist/services/import-export.js +30 -27
- package/dist/services/items.d.ts +3 -3
- package/dist/services/items.js +42 -36
- package/dist/services/mail/index.d.ts +4 -4
- package/dist/services/mail/index.js +14 -10
- package/dist/services/meta.d.ts +3 -3
- package/dist/services/meta.js +11 -9
- package/dist/services/notifications.d.ts +3 -3
- package/dist/services/notifications.js +10 -9
- package/dist/services/operations.d.ts +2 -2
- package/dist/services/panels.d.ts +1 -1
- package/dist/services/payload.d.ts +3 -3
- package/dist/services/payload.js +124 -122
- package/dist/services/permissions.d.ts +3 -3
- package/dist/services/permissions.js +11 -11
- package/dist/services/presets.d.ts +1 -1
- package/dist/services/relations.d.ts +6 -6
- package/dist/services/relations.js +45 -43
- package/dist/services/revisions.d.ts +1 -1
- package/dist/services/revisions.js +3 -3
- package/dist/services/roles.d.ts +2 -2
- package/dist/services/roles.js +7 -7
- package/dist/services/schema.d.ts +3 -3
- package/dist/services/schema.js +9 -11
- package/dist/services/server.d.ts +3 -3
- package/dist/services/server.js +88 -32
- package/dist/services/settings.d.ts +1 -1
- package/dist/services/shares.d.ts +1 -1
- package/dist/services/shares.js +14 -15
- package/dist/services/specifications.d.ts +4 -4
- package/dist/services/specifications.js +137 -119
- package/dist/services/tfa.d.ts +2 -2
- package/dist/services/tfa.js +7 -5
- package/dist/services/users.d.ts +2 -6
- package/dist/services/users.js +37 -40
- package/dist/services/utils.d.ts +3 -3
- package/dist/services/utils.js +10 -8
- package/dist/services/webhooks.d.ts +2 -2
- package/dist/services/webhooks.js +2 -1
- package/dist/storage/register-locations.js +1 -1
- package/dist/types/assets.d.ts +1 -1
- package/dist/types/ast.d.ts +1 -1
- package/dist/types/auth.d.ts +2 -2
- package/dist/types/collection.d.ts +2 -2
- package/dist/types/events.d.ts +2 -2
- package/dist/types/graphql.d.ts +2 -2
- package/dist/types/items.d.ts +3 -3
- package/dist/types/services.d.ts +5 -5
- package/dist/types/snapshot.d.ts +4 -4
- package/dist/utils/apply-diff.d.ts +3 -3
- package/dist/utils/apply-diff.js +25 -28
- package/dist/utils/apply-query.d.ts +3 -3
- package/dist/utils/apply-query.js +10 -12
- package/dist/utils/apply-snapshot.d.ts +3 -3
- package/dist/utils/apply-snapshot.js +5 -6
- package/dist/utils/construct-flow-tree.d.ts +1 -1
- package/dist/utils/construct-flow-tree.js +2 -2
- package/dist/utils/dynamic-import.js +1 -1
- package/dist/utils/filter-items.d.ts +1 -1
- package/dist/utils/generate-hash.js +1 -1
- package/dist/utils/get-accountability-for-role.d.ts +2 -2
- package/dist/utils/get-accountability-for-role.js +1 -1
- package/dist/utils/get-ast-from-query.d.ts +3 -3
- package/dist/utils/get-ast-from-query.js +22 -28
- package/dist/utils/get-auth-providers.js +1 -1
- package/dist/utils/get-cache-headers.d.ts +1 -1
- package/dist/utils/get-cache-headers.js +6 -7
- package/dist/utils/get-cache-key.d.ts +1 -1
- package/dist/utils/get-cache-key.js +2 -3
- package/dist/utils/get-collection-from-alias.d.ts +1 -1
- package/dist/utils/get-collection-from-alias.js +1 -0
- package/dist/utils/get-column-path.d.ts +2 -2
- package/dist/utils/get-column-path.js +3 -4
- package/dist/utils/get-column.d.ts +4 -4
- package/dist/utils/get-column.js +4 -5
- package/dist/utils/get-default-value.d.ts +2 -2
- package/dist/utils/get-default-value.js +2 -3
- package/dist/utils/get-graphql-query-and-variables.d.ts +1 -1
- package/dist/utils/get-graphql-query-and-variables.js +1 -2
- package/dist/utils/get-graphql-type.d.ts +2 -2
- package/dist/utils/get-graphql-type.js +1 -1
- package/dist/utils/get-ip-from-req.d.ts +1 -1
- package/dist/utils/get-ip-from-req.js +2 -2
- package/dist/utils/get-local-type.d.ts +1 -1
- package/dist/utils/get-local-type.js +3 -3
- package/dist/utils/get-milliseconds.js +1 -2
- package/dist/utils/get-permissions.d.ts +1 -1
- package/dist/utils/get-permissions.js +12 -12
- package/dist/utils/get-relation-info.d.ts +1 -1
- package/dist/utils/get-relation-info.js +3 -5
- package/dist/utils/get-relation-type.d.ts +1 -1
- package/dist/utils/get-relation-type.js +3 -4
- package/dist/utils/get-schema.d.ts +2 -2
- package/dist/utils/get-schema.js +20 -22
- package/dist/utils/get-snapshot-diff.js +2 -3
- package/dist/utils/get-snapshot.d.ts +3 -3
- package/dist/utils/get-snapshot.js +6 -8
- package/dist/utils/is-directus-jwt.js +1 -1
- package/dist/utils/is-url-allowed.js +5 -2
- package/dist/utils/job-queue.js +2 -0
- package/dist/utils/jwt.d.ts +1 -1
- package/dist/utils/merge-permissions-for-share.d.ts +1 -1
- package/dist/utils/merge-permissions-for-share.js +3 -4
- package/dist/utils/merge-permissions.d.ts +3 -3
- package/dist/utils/reduce-schema.d.ts +1 -1
- package/dist/utils/reduce-schema.js +12 -12
- package/dist/utils/sanitize-query.d.ts +1 -1
- package/dist/utils/sanitize-query.js +27 -27
- package/dist/utils/sanitize-schema.d.ts +2 -2
- package/dist/utils/should-skip-cache.d.ts +7 -0
- package/dist/utils/should-skip-cache.js +21 -0
- package/dist/utils/should-skip-cache.test.d.ts +1 -0
- package/dist/utils/track.js +16 -16
- package/dist/utils/transformations.d.ts +1 -1
- package/dist/utils/transformations.js +2 -4
- package/dist/utils/url.js +7 -2
- package/dist/utils/user-name.d.ts +1 -1
- package/dist/utils/validate-diff.js +7 -8
- package/dist/utils/validate-keys.d.ts +2 -2
- package/dist/utils/validate-keys.js +1 -1
- package/dist/utils/validate-query.d.ts +1 -1
- package/dist/utils/validate-query.js +3 -3
- package/dist/utils/validate-storage.js +8 -8
- package/dist/webhooks.js +3 -3
- package/package.json +36 -37
- package/dist/utils/with-timeout.d.ts +0 -1
- package/dist/utils/with-timeout.js +0 -16
package/dist/services/users.js
CHANGED
|
@@ -4,22 +4,21 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
4
4
|
};
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
exports.UsersService = void 0;
|
|
7
|
+
const exceptions_1 = require("@directus/shared/exceptions");
|
|
8
|
+
const utils_1 = require("@directus/shared/utils");
|
|
7
9
|
const jsonwebtoken_1 = __importDefault(require("jsonwebtoken"));
|
|
8
10
|
const lodash_1 = require("lodash");
|
|
11
|
+
const perf_hooks_1 = require("perf_hooks");
|
|
9
12
|
const database_1 = __importDefault(require("../database"));
|
|
10
13
|
const env_1 = __importDefault(require("../env"));
|
|
11
|
-
const exceptions_1 = require("@directus/shared/exceptions");
|
|
12
14
|
const exceptions_2 = require("../exceptions");
|
|
13
15
|
const record_not_unique_1 = require("../exceptions/database/record-not-unique");
|
|
14
16
|
const is_url_allowed_1 = __importDefault(require("../utils/is-url-allowed"));
|
|
15
|
-
const
|
|
17
|
+
const stall_1 = require("../utils/stall");
|
|
16
18
|
const url_1 = require("../utils/url");
|
|
17
19
|
const items_1 = require("./items");
|
|
18
20
|
const mail_1 = require("./mail");
|
|
19
21
|
const settings_1 = require("./settings");
|
|
20
|
-
const stall_1 = require("../utils/stall");
|
|
21
|
-
const perf_hooks_1 = require("perf_hooks");
|
|
22
|
-
const utils_2 = require("@directus/shared/utils");
|
|
23
22
|
class UsersService extends items_1.ItemsService {
|
|
24
23
|
constructor(options) {
|
|
25
24
|
super('directus_users', options);
|
|
@@ -96,7 +95,7 @@ class UsersService extends items_1.ItemsService {
|
|
|
96
95
|
.andWhere({ 'directus_roles.admin_access': true })
|
|
97
96
|
.leftJoin('directus_roles', 'directus_users.role', 'directus_roles.id')
|
|
98
97
|
.first();
|
|
99
|
-
const otherAdminUsersCount = +(
|
|
98
|
+
const otherAdminUsersCount = +(otherAdminUsers?.count || 0);
|
|
100
99
|
if (otherAdminUsersCount === 0) {
|
|
101
100
|
throw new exceptions_2.UnprocessableEntityException(`You can't remove the last admin user from the role.`);
|
|
102
101
|
}
|
|
@@ -113,7 +112,7 @@ class UsersService extends items_1.ItemsService {
|
|
|
113
112
|
.andWhere({ 'directus_users.status': 'active' })
|
|
114
113
|
.leftJoin('directus_roles', 'directus_users.role', 'directus_roles.id')
|
|
115
114
|
.first();
|
|
116
|
-
const otherAdminUsersCount = +(
|
|
115
|
+
const otherAdminUsersCount = +(otherAdminUsers?.count || 0);
|
|
117
116
|
if (otherAdminUsersCount === 0) {
|
|
118
117
|
throw new exceptions_2.UnprocessableEntityException(`You can't change the active status of the last admin user.`);
|
|
119
118
|
}
|
|
@@ -129,8 +128,8 @@ class UsersService extends items_1.ItemsService {
|
|
|
129
128
|
* Create multiple new users
|
|
130
129
|
*/
|
|
131
130
|
async createMany(data, opts) {
|
|
132
|
-
const emails = data
|
|
133
|
-
const passwords = data
|
|
131
|
+
const emails = data['map']((payload) => payload['email']).filter((email) => email);
|
|
132
|
+
const passwords = data['map']((payload) => payload['password']).filter((password) => password);
|
|
134
133
|
try {
|
|
135
134
|
if (emails.length) {
|
|
136
135
|
await this.checkUniqueEmails(emails);
|
|
@@ -179,46 +178,45 @@ class UsersService extends items_1.ItemsService {
|
|
|
179
178
|
* Update many users by primary key
|
|
180
179
|
*/
|
|
181
180
|
async updateMany(keys, data, opts) {
|
|
182
|
-
var _a, _b;
|
|
183
181
|
try {
|
|
184
|
-
if (data
|
|
185
|
-
// data
|
|
186
|
-
const roleId =
|
|
182
|
+
if (data['role']) {
|
|
183
|
+
// data['role'] will be an object with id with GraphQL mutations
|
|
184
|
+
const roleId = data['role']?.id ?? data['role'];
|
|
187
185
|
const newRole = await this.knex.select('admin_access').from('directus_roles').where('id', roleId).first();
|
|
188
|
-
if (!
|
|
186
|
+
if (!newRole?.admin_access) {
|
|
189
187
|
await this.checkRemainingAdminExistence(keys);
|
|
190
188
|
}
|
|
191
189
|
}
|
|
192
|
-
if (data
|
|
190
|
+
if (data['status'] !== undefined && data['status'] !== 'active') {
|
|
193
191
|
await this.checkRemainingActiveAdmin(keys);
|
|
194
192
|
}
|
|
195
|
-
if (data
|
|
193
|
+
if (data['email']) {
|
|
196
194
|
if (keys.length > 1) {
|
|
197
195
|
throw new record_not_unique_1.RecordNotUniqueException('email', {
|
|
198
196
|
collection: 'directus_users',
|
|
199
197
|
field: 'email',
|
|
200
|
-
invalid: data
|
|
198
|
+
invalid: data['email'],
|
|
201
199
|
});
|
|
202
200
|
}
|
|
203
|
-
await this.checkUniqueEmails([data
|
|
201
|
+
await this.checkUniqueEmails([data['email']], keys[0]);
|
|
204
202
|
}
|
|
205
|
-
if (data
|
|
206
|
-
await this.checkPasswordPolicy([data
|
|
203
|
+
if (data['password']) {
|
|
204
|
+
await this.checkPasswordPolicy([data['password']]);
|
|
207
205
|
}
|
|
208
|
-
if (data
|
|
206
|
+
if (data['tfa_secret'] !== undefined) {
|
|
209
207
|
throw new exceptions_2.InvalidPayloadException(`You can't change the "tfa_secret" value manually.`);
|
|
210
208
|
}
|
|
211
|
-
if (data
|
|
209
|
+
if (data['provider'] !== undefined) {
|
|
212
210
|
if (this.accountability && this.accountability.admin !== true) {
|
|
213
211
|
throw new exceptions_2.InvalidPayloadException(`You can't change the "provider" value manually.`);
|
|
214
212
|
}
|
|
215
|
-
data
|
|
213
|
+
data['auth_data'] = null;
|
|
216
214
|
}
|
|
217
|
-
if (data
|
|
215
|
+
if (data['external_identifier'] !== undefined) {
|
|
218
216
|
if (this.accountability && this.accountability.admin !== true) {
|
|
219
217
|
throw new exceptions_2.InvalidPayloadException(`You can't change the "external_identifier" value manually.`);
|
|
220
218
|
}
|
|
221
|
-
data
|
|
219
|
+
data['auth_data'] = null;
|
|
222
220
|
}
|
|
223
221
|
}
|
|
224
222
|
catch (err) {
|
|
@@ -265,7 +263,7 @@ class UsersService extends items_1.ItemsService {
|
|
|
265
263
|
async inviteUser(email, role, url, subject) {
|
|
266
264
|
const opts = {};
|
|
267
265
|
try {
|
|
268
|
-
if (url && (0, is_url_allowed_1.default)(url, env_1.default
|
|
266
|
+
if (url && (0, is_url_allowed_1.default)(url, env_1.default['USER_INVITE_URL_ALLOW_LIST']) === false) {
|
|
269
267
|
throw new exceptions_2.InvalidPayloadException(`Url "${url}" can't be used to invite users.`);
|
|
270
268
|
}
|
|
271
269
|
}
|
|
@@ -279,9 +277,9 @@ class UsersService extends items_1.ItemsService {
|
|
|
279
277
|
});
|
|
280
278
|
for (const email of emails) {
|
|
281
279
|
const payload = { email, scope: 'invite' };
|
|
282
|
-
const token = jsonwebtoken_1.default.sign(payload, env_1.default
|
|
283
|
-
const subjectLine = subject
|
|
284
|
-
const inviteURL = url ? new url_1.Url(url) : new url_1.Url(env_1.default
|
|
280
|
+
const token = jsonwebtoken_1.default.sign(payload, env_1.default['SECRET'], { expiresIn: '7d', issuer: 'directus' });
|
|
281
|
+
const subjectLine = subject ?? "You've been invited";
|
|
282
|
+
const inviteURL = url ? new url_1.Url(url) : new url_1.Url(env_1.default['PUBLIC_URL']).addPath('admin', 'accept-invite');
|
|
285
283
|
inviteURL.setQuery('token', token);
|
|
286
284
|
// Create user first to verify uniqueness
|
|
287
285
|
await this.createOne({ email, role, status: 'invited' }, opts);
|
|
@@ -299,11 +297,11 @@ class UsersService extends items_1.ItemsService {
|
|
|
299
297
|
}
|
|
300
298
|
}
|
|
301
299
|
async acceptInvite(token, password) {
|
|
302
|
-
const { email, scope } = jsonwebtoken_1.default.verify(token, env_1.default
|
|
300
|
+
const { email, scope } = jsonwebtoken_1.default.verify(token, env_1.default['SECRET'], { issuer: 'directus' });
|
|
303
301
|
if (scope !== 'invite')
|
|
304
302
|
throw new exceptions_2.ForbiddenException();
|
|
305
303
|
const user = await this.knex.select('id', 'status').from('directus_users').where({ email }).first();
|
|
306
|
-
if (
|
|
304
|
+
if (user?.status !== 'invited') {
|
|
307
305
|
throw new exceptions_2.InvalidPayloadException(`Email address ${email} hasn't been invited.`);
|
|
308
306
|
}
|
|
309
307
|
// Allow unauthenticated update
|
|
@@ -321,11 +319,11 @@ class UsersService extends items_1.ItemsService {
|
|
|
321
319
|
.from('directus_users')
|
|
322
320
|
.whereRaw('LOWER(??) = ?', ['email', email.toLowerCase()])
|
|
323
321
|
.first();
|
|
324
|
-
if (
|
|
322
|
+
if (user?.status !== 'active') {
|
|
325
323
|
await (0, stall_1.stall)(STALL_TIME, timeStart);
|
|
326
324
|
throw new exceptions_2.ForbiddenException();
|
|
327
325
|
}
|
|
328
|
-
if (url && (0, is_url_allowed_1.default)(url, env_1.default
|
|
326
|
+
if (url && (0, is_url_allowed_1.default)(url, env_1.default['PASSWORD_RESET_URL_ALLOW_LIST']) === false) {
|
|
329
327
|
throw new exceptions_2.InvalidPayloadException(`Url "${url}" can't be used to reset passwords.`);
|
|
330
328
|
}
|
|
331
329
|
const mailService = new mail_1.MailService({
|
|
@@ -333,11 +331,11 @@ class UsersService extends items_1.ItemsService {
|
|
|
333
331
|
knex: this.knex,
|
|
334
332
|
accountability: this.accountability,
|
|
335
333
|
});
|
|
336
|
-
const payload = { email, scope: 'password-reset', hash: (0,
|
|
337
|
-
const token = jsonwebtoken_1.default.sign(payload, env_1.default
|
|
334
|
+
const payload = { email, scope: 'password-reset', hash: (0, utils_1.getSimpleHash)('' + user.password) };
|
|
335
|
+
const token = jsonwebtoken_1.default.sign(payload, env_1.default['SECRET'], { expiresIn: '1d', issuer: 'directus' });
|
|
338
336
|
const acceptURL = url
|
|
339
337
|
? new url_1.Url(url).setQuery('token', token).toString()
|
|
340
|
-
: new url_1.Url(env_1.default
|
|
338
|
+
: new url_1.Url(env_1.default['PUBLIC_URL']).addPath('admin', 'reset-password').setQuery('token', token);
|
|
341
339
|
const subjectLine = subject ? subject : 'Password Reset Request';
|
|
342
340
|
await mailService.send({
|
|
343
341
|
to: email,
|
|
@@ -353,8 +351,7 @@ class UsersService extends items_1.ItemsService {
|
|
|
353
351
|
await (0, stall_1.stall)(STALL_TIME, timeStart);
|
|
354
352
|
}
|
|
355
353
|
async resetPassword(token, password) {
|
|
356
|
-
|
|
357
|
-
const { email, scope, hash } = jsonwebtoken_1.default.verify(token, env_1.default.SECRET, { issuer: 'directus' });
|
|
354
|
+
const { email, scope, hash } = jsonwebtoken_1.default.verify(token, env_1.default['SECRET'], { issuer: 'directus' });
|
|
358
355
|
if (scope !== 'password-reset' || !hash)
|
|
359
356
|
throw new exceptions_2.ForbiddenException();
|
|
360
357
|
const opts = {};
|
|
@@ -365,7 +362,7 @@ class UsersService extends items_1.ItemsService {
|
|
|
365
362
|
opts.preMutationException = err;
|
|
366
363
|
}
|
|
367
364
|
const user = await this.knex.select('id', 'status', 'password').from('directus_users').where({ email }).first();
|
|
368
|
-
if (
|
|
365
|
+
if (user?.status !== 'active' || hash !== (0, utils_1.getSimpleHash)('' + user.password)) {
|
|
369
366
|
throw new exceptions_2.ForbiddenException();
|
|
370
367
|
}
|
|
371
368
|
// Allow unauthenticated update
|
|
@@ -373,7 +370,7 @@ class UsersService extends items_1.ItemsService {
|
|
|
373
370
|
knex: this.knex,
|
|
374
371
|
schema: this.schema,
|
|
375
372
|
accountability: {
|
|
376
|
-
...(
|
|
373
|
+
...(this.accountability ?? { role: null }),
|
|
377
374
|
admin: true, // We need to skip permissions checks for the update call below
|
|
378
375
|
},
|
|
379
376
|
});
|
package/dist/services/utils.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
1
|
+
import type { Accountability, SchemaOverview } from '@directus/shared/types';
|
|
2
|
+
import type { Knex } from 'knex';
|
|
3
|
+
import type { AbstractServiceOptions, PrimaryKey } from '../types';
|
|
4
4
|
export declare class UtilsService {
|
|
5
5
|
knex: Knex;
|
|
6
6
|
accountability: Accountability | null;
|
package/dist/services/utils.js
CHANGED
|
@@ -6,30 +6,32 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
6
6
|
exports.UtilsService = void 0;
|
|
7
7
|
const database_1 = __importDefault(require("../database"));
|
|
8
8
|
const collections_1 = require("../database/system-data/collections");
|
|
9
|
-
const exceptions_1 = require("../exceptions");
|
|
10
9
|
const emitter_1 = __importDefault(require("../emitter"));
|
|
10
|
+
const exceptions_1 = require("../exceptions");
|
|
11
11
|
class UtilsService {
|
|
12
|
+
knex;
|
|
13
|
+
accountability;
|
|
14
|
+
schema;
|
|
12
15
|
constructor(options) {
|
|
13
16
|
this.knex = options.knex || (0, database_1.default)();
|
|
14
17
|
this.accountability = options.accountability || null;
|
|
15
18
|
this.schema = options.schema;
|
|
16
19
|
}
|
|
17
20
|
async sort(collection, { item, to }) {
|
|
18
|
-
var _a, _b, _c, _d;
|
|
19
21
|
const sortFieldResponse = (await this.knex.select('sort_field').from('directus_collections').where({ collection }).first()) ||
|
|
20
22
|
collections_1.systemCollectionRows;
|
|
21
|
-
const sortField = sortFieldResponse
|
|
23
|
+
const sortField = sortFieldResponse?.sort_field;
|
|
22
24
|
if (!sortField) {
|
|
23
25
|
throw new exceptions_1.InvalidPayloadException(`Collection "${collection}" doesn't have a sort field.`);
|
|
24
26
|
}
|
|
25
|
-
if (
|
|
26
|
-
const permissions =
|
|
27
|
+
if (this.accountability?.admin !== true) {
|
|
28
|
+
const permissions = this.accountability?.permissions?.find((permission) => {
|
|
27
29
|
return permission.collection === collection && permission.action === 'update';
|
|
28
30
|
});
|
|
29
31
|
if (!permissions) {
|
|
30
32
|
throw new exceptions_1.ForbiddenException();
|
|
31
33
|
}
|
|
32
|
-
const allowedFields =
|
|
34
|
+
const allowedFields = permissions.fields ?? [];
|
|
33
35
|
if (allowedFields[0] !== '*' && allowedFields.includes(sortField) === false) {
|
|
34
36
|
throw new exceptions_1.ForbiddenException();
|
|
35
37
|
}
|
|
@@ -37,7 +39,7 @@ class UtilsService {
|
|
|
37
39
|
const primaryKeyField = this.schema.collections[collection].primary;
|
|
38
40
|
// Make sure all rows have a sort value
|
|
39
41
|
const countResponse = await this.knex.count('* as count').from(collection).whereNull(sortField).first();
|
|
40
|
-
if (
|
|
42
|
+
if (countResponse?.count && +countResponse.count !== 0) {
|
|
41
43
|
const lastSortValueResponse = await this.knex.max(sortField).from(collection).first();
|
|
42
44
|
const rowsWithoutSortValue = await this.knex
|
|
43
45
|
.select(primaryKeyField, sortField)
|
|
@@ -59,7 +61,7 @@ class UtilsService {
|
|
|
59
61
|
.groupBy(sortField)
|
|
60
62
|
.from(collection)
|
|
61
63
|
.havingRaw('count(??) > 1', [sortField]);
|
|
62
|
-
if (
|
|
64
|
+
if (duplicates?.length > 0) {
|
|
63
65
|
const ids = await this.knex.select(primaryKeyField).from(collection).orderBy(sortField);
|
|
64
66
|
// This might not scale that well, but I don't really know how to accurately set all rows
|
|
65
67
|
// to a sequential value that works cross-DB vendor otherwise
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { AbstractServiceOptions, Item, PrimaryKey, Webhook, MutationOptions } from '../types';
|
|
2
|
-
import { ItemsService } from './items';
|
|
3
1
|
import { Messenger } from '../messenger';
|
|
2
|
+
import type { AbstractServiceOptions, Item, MutationOptions, PrimaryKey, Webhook } from '../types';
|
|
3
|
+
import { ItemsService } from './items';
|
|
4
4
|
export declare class WebhooksService extends ItemsService<Webhook> {
|
|
5
5
|
messenger: Messenger;
|
|
6
6
|
constructor(options: AbstractServiceOptions);
|
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.WebhooksService = void 0;
|
|
4
|
-
const items_1 = require("./items");
|
|
5
4
|
const messenger_1 = require("../messenger");
|
|
5
|
+
const items_1 = require("./items");
|
|
6
6
|
class WebhooksService extends items_1.ItemsService {
|
|
7
|
+
messenger;
|
|
7
8
|
constructor(options) {
|
|
8
9
|
super('directus_webhooks', options);
|
|
9
10
|
this.messenger = (0, messenger_1.getMessenger)();
|
|
@@ -6,7 +6,7 @@ const env_1 = require("../env");
|
|
|
6
6
|
const get_config_from_env_1 = require("../utils/get-config-from-env");
|
|
7
7
|
const registerLocations = async (storage) => {
|
|
8
8
|
const env = (0, env_1.getEnv)();
|
|
9
|
-
const locations = (0, utils_1.toArray)(env
|
|
9
|
+
const locations = (0, utils_1.toArray)(env['STORAGE_LOCATIONS']);
|
|
10
10
|
locations.forEach((location) => {
|
|
11
11
|
location = location.trim();
|
|
12
12
|
const driverConfig = (0, get_config_from_env_1.getConfigFromEnv)(`STORAGE_${location.toUpperCase()}_`);
|
package/dist/types/assets.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ResizeOptions, Sharp } from 'sharp';
|
|
1
|
+
import type { ResizeOptions, Sharp } from 'sharp';
|
|
2
2
|
export declare const TransformationMethods: readonly ["toFormat", "jpeg", "png", "tiff", "webp", "resize", "extend", "extract", "trim", "rotate", "flip", "flop", "sharpen", "median", "blur", "flatten", "gamma", "negate", "normalise", "normalize", "clahe", "convolve", "threshold", "linear", "recomb", "modulate", "tint", "greyscale", "grayscale", "toColorspace", "toColourspace", "removeAlpha", "ensureAlpha", "extractChannel", "bandbool"];
|
|
3
3
|
type AllowedSharpMethods = Pick<Sharp, (typeof TransformationMethods)[number]>;
|
|
4
4
|
export type TransformationMap = {
|
package/dist/types/ast.d.ts
CHANGED
package/dist/types/auth.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
1
|
+
import type { Field } from '@directus/shared/types';
|
|
2
|
+
import type { Table } from 'knex-schema-inspector/dist/types/table';
|
|
3
3
|
export type CollectionMeta = {
|
|
4
4
|
collection: string;
|
|
5
5
|
note: string | null;
|
package/dist/types/events.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { ActionHandler, FilterHandler, InitHandler } from '@directus/shared/types';
|
|
2
|
-
import { ScheduledTask } from 'node-cron';
|
|
1
|
+
import type { ActionHandler, FilterHandler, InitHandler } from '@directus/shared/types';
|
|
2
|
+
import type { ScheduledTask } from 'node-cron';
|
|
3
3
|
export type EventHandler = {
|
|
4
4
|
type: 'filter';
|
|
5
5
|
name: string;
|
package/dist/types/graphql.d.ts
CHANGED
package/dist/types/items.d.ts
CHANGED
|
@@ -2,8 +2,8 @@
|
|
|
2
2
|
* I know this looks a little silly, but it allows us to explicitly differentiate between when we're
|
|
3
3
|
* expecting an item vs any other generic object.
|
|
4
4
|
*/
|
|
5
|
-
import { BaseException } from '@directus/shared/exceptions';
|
|
6
|
-
import { EventContext } from '@directus/shared/types';
|
|
5
|
+
import type { BaseException } from '@directus/shared/exceptions';
|
|
6
|
+
import type { EventContext } from '@directus/shared/types';
|
|
7
7
|
export type Item = Record<string, any>;
|
|
8
8
|
export type PrimaryKey = string | number;
|
|
9
9
|
export type Alterations = {
|
|
@@ -31,7 +31,7 @@ export type MutationOptions = {
|
|
|
31
31
|
/**
|
|
32
32
|
* Allow disabling the emitting of hooks. Useful if a custom hook is fired (like files.upload)
|
|
33
33
|
*/
|
|
34
|
-
emitEvents?: boolean;
|
|
34
|
+
emitEvents?: boolean | undefined;
|
|
35
35
|
/**
|
|
36
36
|
* To bypass the emitting of action events if emitEvents is enabled
|
|
37
37
|
* Can be used to queue up the nested events from item service's create, update and delete
|
package/dist/types/services.d.ts
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import { Item, PrimaryKey } from './items';
|
|
1
|
+
import type { Accountability, Query, SchemaOverview } from '@directus/shared/types';
|
|
2
|
+
import type { Knex } from 'knex';
|
|
3
|
+
import type { Item, PrimaryKey } from './items';
|
|
4
4
|
export type AbstractServiceOptions = {
|
|
5
5
|
knex?: Knex;
|
|
6
|
-
accountability?: Accountability | null;
|
|
6
|
+
accountability?: Accountability | null | undefined;
|
|
7
7
|
schema: SchemaOverview;
|
|
8
8
|
};
|
|
9
9
|
export interface AbstractService {
|
|
10
10
|
knex: Knex;
|
|
11
|
-
accountability: Accountability | null;
|
|
11
|
+
accountability: Accountability | null | undefined;
|
|
12
12
|
createOne(data: Partial<Item>): Promise<PrimaryKey>;
|
|
13
13
|
createMany(data: Partial<Item>[]): Promise<PrimaryKey[]>;
|
|
14
14
|
readOne(key: PrimaryKey, query?: Query): Promise<Item>;
|
package/dist/types/snapshot.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import { DatabaseClient } from './database';
|
|
1
|
+
import type { Field, FieldMeta, Relation, RelationMeta } from '@directus/shared/types';
|
|
2
|
+
import type { Diff } from 'deep-diff';
|
|
3
|
+
import type { Collection } from './collection';
|
|
4
|
+
import type { DatabaseClient } from './database';
|
|
5
5
|
export type Snapshot = {
|
|
6
6
|
version: number;
|
|
7
7
|
directus: string;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { SchemaOverview } from '@directus/shared/types';
|
|
2
|
-
import { Knex } from 'knex';
|
|
3
|
-
import { Snapshot, SnapshotDiff, SnapshotField } from '../types';
|
|
1
|
+
import type { SchemaOverview } from '@directus/shared/types';
|
|
4
2
|
import { Diff } from 'deep-diff';
|
|
3
|
+
import type { Knex } from 'knex';
|
|
4
|
+
import { Snapshot, SnapshotDiff, SnapshotField } from '../types';
|
|
5
5
|
export declare function applyDiff(currentSnapshot: Snapshot, snapshotDiff: SnapshotDiff, options?: {
|
|
6
6
|
database?: Knex;
|
|
7
7
|
schema?: SchemaOverview;
|
package/dist/utils/apply-diff.js
CHANGED
|
@@ -4,19 +4,18 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
4
4
|
};
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
exports.isNestedMetaUpdate = exports.applyDiff = void 0;
|
|
7
|
-
const services_1 = require("../services");
|
|
8
|
-
const types_1 = require("../types");
|
|
9
|
-
const get_schema_1 = require("./get-schema");
|
|
10
|
-
const database_1 = __importDefault(require("../database"));
|
|
11
7
|
const deep_diff_1 = require("deep-diff");
|
|
12
8
|
const lodash_1 = require("lodash");
|
|
13
|
-
const logger_1 = __importDefault(require("../logger"));
|
|
14
|
-
const emitter_1 = __importDefault(require("../emitter"));
|
|
15
9
|
const cache_1 = require("../cache");
|
|
10
|
+
const database_1 = __importDefault(require("../database"));
|
|
11
|
+
const emitter_1 = __importDefault(require("../emitter"));
|
|
12
|
+
const logger_1 = __importDefault(require("../logger"));
|
|
13
|
+
const services_1 = require("../services");
|
|
14
|
+
const types_1 = require("../types");
|
|
15
|
+
const get_schema_1 = require("./get-schema");
|
|
16
16
|
async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
17
|
-
|
|
18
|
-
const
|
|
19
|
-
const schema = (_b = options === null || options === void 0 ? void 0 : options.schema) !== null && _b !== void 0 ? _b : (await (0, get_schema_1.getSchema)({ database, bypassCache: true }));
|
|
17
|
+
const database = options?.database ?? (0, database_1.default)();
|
|
18
|
+
const schema = options?.schema ?? (await (0, get_schema_1.getSchema)({ database, bypassCache: true }));
|
|
20
19
|
const nestedActionEvents = [];
|
|
21
20
|
const mutationOptions = {
|
|
22
21
|
autoPurgeSystemCache: false,
|
|
@@ -24,24 +23,23 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
24
23
|
};
|
|
25
24
|
await database.transaction(async (trx) => {
|
|
26
25
|
const collectionsService = new services_1.CollectionsService({ knex: trx, schema });
|
|
27
|
-
const getNestedCollectionsToCreate = (currentLevelCollection) => snapshotDiff.collections.filter(({ diff }) =>
|
|
28
|
-
const getNestedCollectionsToDelete = (currentLevelCollection) => snapshotDiff.collections.filter(({ diff }) =>
|
|
26
|
+
const getNestedCollectionsToCreate = (currentLevelCollection) => snapshotDiff.collections.filter(({ diff }) => diff[0].rhs?.meta?.group === currentLevelCollection);
|
|
27
|
+
const getNestedCollectionsToDelete = (currentLevelCollection) => snapshotDiff.collections.filter(({ diff }) => diff[0].lhs?.meta?.group === currentLevelCollection);
|
|
29
28
|
const createCollections = async (collections) => {
|
|
30
29
|
for (const { collection, diff } of collections) {
|
|
31
|
-
if (
|
|
30
|
+
if (diff?.[0].kind === types_1.DiffKind.NEW && diff[0].rhs) {
|
|
32
31
|
// We'll nest the to-be-created fields in the same collection creation, to prevent
|
|
33
32
|
// creating a collection without a primary key
|
|
34
33
|
const fields = snapshotDiff.fields
|
|
35
34
|
.filter((fieldDiff) => fieldDiff.collection === collection)
|
|
36
35
|
.map((fieldDiff) => fieldDiff.diff[0].rhs)
|
|
37
36
|
.map((fieldDiff) => {
|
|
38
|
-
var _a, _b, _c, _d, _e;
|
|
39
37
|
// Casts field type to UUID when applying non-PostgreSQL schema onto PostgreSQL database.
|
|
40
38
|
// This is needed because they snapshots UUID fields as char/varchar with length 36.
|
|
41
|
-
if (['char', 'varchar'].includes(String(
|
|
42
|
-
|
|
43
|
-
(
|
|
44
|
-
(
|
|
39
|
+
if (['char', 'varchar'].includes(String(fieldDiff.schema?.data_type).toLowerCase()) &&
|
|
40
|
+
fieldDiff.schema?.max_length === 36 &&
|
|
41
|
+
(fieldDiff.schema?.is_primary_key ||
|
|
42
|
+
(fieldDiff.schema?.foreign_key_table && fieldDiff.schema?.foreign_key_column))) {
|
|
45
43
|
return (0, lodash_1.merge)(fieldDiff, { type: 'uuid', schema: { data_type: 'uuid', max_length: null } });
|
|
46
44
|
}
|
|
47
45
|
else {
|
|
@@ -66,7 +64,7 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
66
64
|
};
|
|
67
65
|
const deleteCollections = async (collections) => {
|
|
68
66
|
for (const { collection, diff } of collections) {
|
|
69
|
-
if (
|
|
67
|
+
if (diff?.[0].kind === types_1.DiffKind.DELETE) {
|
|
70
68
|
const relations = schema.relations.filter((r) => r.related_collection === collection || r.collection === collection);
|
|
71
69
|
if (relations.length > 0) {
|
|
72
70
|
const relationsService = new services_1.RelationsService({ knex: trx, schema });
|
|
@@ -95,13 +93,12 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
95
93
|
};
|
|
96
94
|
// Finds all collections that need to be created
|
|
97
95
|
const filterCollectionsForCreation = ({ diff }) => {
|
|
98
|
-
var _a;
|
|
99
96
|
// Check new collections only
|
|
100
97
|
const isNewCollection = diff[0].kind === types_1.DiffKind.NEW;
|
|
101
98
|
if (!isNewCollection)
|
|
102
99
|
return false;
|
|
103
100
|
// Create now if no group
|
|
104
|
-
const groupName =
|
|
101
|
+
const groupName = diff[0].rhs.meta?.group;
|
|
105
102
|
if (!groupName)
|
|
106
103
|
return true;
|
|
107
104
|
// Check if parent collection already exists in schema
|
|
@@ -124,9 +121,9 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
124
121
|
// then continue with nested collections recursively
|
|
125
122
|
await createCollections(snapshotDiff.collections.filter(filterCollectionsForCreation));
|
|
126
123
|
// delete top level collections (no group) first, then continue with nested collections recursively
|
|
127
|
-
await deleteCollections(snapshotDiff.collections.filter(({ diff }) =>
|
|
124
|
+
await deleteCollections(snapshotDiff.collections.filter(({ diff }) => diff[0].kind === types_1.DiffKind.DELETE && diff[0].lhs.meta?.group === null));
|
|
128
125
|
for (const { collection, diff } of snapshotDiff.collections) {
|
|
129
|
-
if (
|
|
126
|
+
if (diff?.[0].kind === types_1.DiffKind.EDIT || diff?.[0].kind === types_1.DiffKind.ARRAY) {
|
|
130
127
|
const currentCollection = currentSnapshot.collections.find((field) => {
|
|
131
128
|
return field.collection === collection;
|
|
132
129
|
});
|
|
@@ -150,7 +147,7 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
150
147
|
schema: await (0, get_schema_1.getSchema)({ database: trx, bypassCache: true }),
|
|
151
148
|
});
|
|
152
149
|
for (const { collection, field, diff } of snapshotDiff.fields) {
|
|
153
|
-
if (
|
|
150
|
+
if (diff?.[0].kind === types_1.DiffKind.NEW && !isNestedMetaUpdate(diff?.[0])) {
|
|
154
151
|
try {
|
|
155
152
|
await fieldsService.createField(collection, diff[0].rhs, undefined, mutationOptions);
|
|
156
153
|
}
|
|
@@ -159,7 +156,7 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
159
156
|
throw err;
|
|
160
157
|
}
|
|
161
158
|
}
|
|
162
|
-
if (
|
|
159
|
+
if (diff?.[0].kind === types_1.DiffKind.EDIT || diff?.[0].kind === types_1.DiffKind.ARRAY || isNestedMetaUpdate(diff?.[0])) {
|
|
163
160
|
const currentField = currentSnapshot.fields.find((snapshotField) => {
|
|
164
161
|
return snapshotField.collection === collection && snapshotField.field === field;
|
|
165
162
|
});
|
|
@@ -177,7 +174,7 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
177
174
|
}
|
|
178
175
|
}
|
|
179
176
|
}
|
|
180
|
-
if (
|
|
177
|
+
if (diff?.[0].kind === types_1.DiffKind.DELETE && !isNestedMetaUpdate(diff?.[0])) {
|
|
181
178
|
try {
|
|
182
179
|
await fieldsService.deleteField(collection, field, mutationOptions);
|
|
183
180
|
}
|
|
@@ -199,7 +196,7 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
199
196
|
for (const diffEdit of diff) {
|
|
200
197
|
(0, lodash_1.set)(structure, diffEdit.path, undefined);
|
|
201
198
|
}
|
|
202
|
-
if (
|
|
199
|
+
if (diff?.[0].kind === types_1.DiffKind.NEW) {
|
|
203
200
|
try {
|
|
204
201
|
await relationsService.createOne(diff[0].rhs, mutationOptions);
|
|
205
202
|
}
|
|
@@ -208,7 +205,7 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
208
205
|
throw err;
|
|
209
206
|
}
|
|
210
207
|
}
|
|
211
|
-
if (
|
|
208
|
+
if (diff?.[0].kind === types_1.DiffKind.EDIT || diff?.[0].kind === types_1.DiffKind.ARRAY) {
|
|
212
209
|
const currentRelation = currentSnapshot.relations.find((relation) => {
|
|
213
210
|
return relation.collection === collection && relation.field === field;
|
|
214
211
|
});
|
|
@@ -226,7 +223,7 @@ async function applyDiff(currentSnapshot, snapshotDiff, options) {
|
|
|
226
223
|
}
|
|
227
224
|
}
|
|
228
225
|
}
|
|
229
|
-
if (
|
|
226
|
+
if (diff?.[0].kind === types_1.DiffKind.DELETE) {
|
|
230
227
|
try {
|
|
231
228
|
await relationsService.deleteOne(collection, field, mutationOptions);
|
|
232
229
|
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { Aggregate, Filter, Query, SchemaOverview } from '@directus/shared/types';
|
|
2
|
-
import { Knex } from 'knex';
|
|
1
|
+
import type { Aggregate, Filter, Query, SchemaOverview } from '@directus/shared/types';
|
|
2
|
+
import type { Knex } from 'knex';
|
|
3
3
|
import { AliasMap } from './get-column-path';
|
|
4
4
|
export declare const generateAlias: (size?: number | undefined) => string;
|
|
5
5
|
/**
|
|
@@ -8,7 +8,7 @@ export declare const generateAlias: (size?: number | undefined) => string;
|
|
|
8
8
|
export default function applyQuery(knex: Knex, collection: string, dbQuery: Knex.QueryBuilder, query: Query, schema: SchemaOverview, options?: {
|
|
9
9
|
aliasMap?: AliasMap;
|
|
10
10
|
isInnerQuery?: boolean;
|
|
11
|
-
hasMultiRelationalSort?: boolean;
|
|
11
|
+
hasMultiRelationalSort?: boolean | undefined;
|
|
12
12
|
}): {
|
|
13
13
|
query: Knex.QueryBuilder<any, any>;
|
|
14
14
|
hasMultiRelationalFilter: boolean;
|