activerecord 5.2.8 → 7.0.2
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of activerecord might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/CHANGELOG.md +1393 -587
- data/MIT-LICENSE +3 -1
- data/README.rdoc +7 -5
- data/examples/performance.rb +1 -1
- data/lib/active_record/aggregations.rb +10 -9
- data/lib/active_record/association_relation.rb +22 -12
- data/lib/active_record/associations/alias_tracker.rb +19 -16
- data/lib/active_record/associations/association.rb +122 -47
- data/lib/active_record/associations/association_scope.rb +24 -24
- data/lib/active_record/associations/belongs_to_association.rb +67 -49
- data/lib/active_record/associations/belongs_to_polymorphic_association.rb +16 -7
- data/lib/active_record/associations/builder/association.rb +52 -23
- data/lib/active_record/associations/builder/belongs_to.rb +44 -61
- data/lib/active_record/associations/builder/collection_association.rb +17 -19
- data/lib/active_record/associations/builder/has_and_belongs_to_many.rb +17 -41
- data/lib/active_record/associations/builder/has_many.rb +10 -3
- data/lib/active_record/associations/builder/has_one.rb +35 -3
- data/lib/active_record/associations/builder/singular_association.rb +5 -3
- data/lib/active_record/associations/collection_association.rb +59 -50
- data/lib/active_record/associations/collection_proxy.rb +32 -23
- data/lib/active_record/associations/disable_joins_association_scope.rb +59 -0
- data/lib/active_record/associations/foreign_association.rb +20 -0
- data/lib/active_record/associations/has_many_association.rb +27 -14
- data/lib/active_record/associations/has_many_through_association.rb +26 -19
- data/lib/active_record/associations/has_one_association.rb +52 -37
- data/lib/active_record/associations/has_one_through_association.rb +6 -6
- data/lib/active_record/associations/join_dependency/join_association.rb +44 -22
- data/lib/active_record/associations/join_dependency/join_part.rb +5 -5
- data/lib/active_record/associations/join_dependency.rb +97 -62
- data/lib/active_record/associations/preloader/association.rb +220 -60
- data/lib/active_record/associations/preloader/batch.rb +48 -0
- data/lib/active_record/associations/preloader/branch.rb +147 -0
- data/lib/active_record/associations/preloader/through_association.rb +85 -40
- data/lib/active_record/associations/preloader.rb +44 -105
- data/lib/active_record/associations/singular_association.rb +9 -17
- data/lib/active_record/associations/through_association.rb +4 -4
- data/lib/active_record/associations.rb +207 -66
- data/lib/active_record/asynchronous_queries_tracker.rb +60 -0
- data/lib/active_record/attribute_assignment.rb +17 -19
- data/lib/active_record/attribute_methods/before_type_cast.rb +19 -8
- data/lib/active_record/attribute_methods/dirty.rb +141 -47
- data/lib/active_record/attribute_methods/primary_key.rb +22 -27
- data/lib/active_record/attribute_methods/query.rb +6 -10
- data/lib/active_record/attribute_methods/read.rb +15 -55
- data/lib/active_record/attribute_methods/serialization.rb +77 -18
- data/lib/active_record/attribute_methods/time_zone_conversion.rb +16 -18
- data/lib/active_record/attribute_methods/write.rb +18 -37
- data/lib/active_record/attribute_methods.rb +90 -153
- data/lib/active_record/attributes.rb +38 -12
- data/lib/active_record/autosave_association.rb +50 -50
- data/lib/active_record/base.rb +23 -18
- data/lib/active_record/callbacks.rb +159 -44
- data/lib/active_record/coders/yaml_column.rb +12 -3
- data/lib/active_record/connection_adapters/abstract/connection_handler.rb +292 -0
- data/lib/active_record/connection_adapters/abstract/connection_pool/queue.rb +209 -0
- data/lib/active_record/connection_adapters/abstract/connection_pool/reaper.rb +76 -0
- data/lib/active_record/connection_adapters/abstract/connection_pool.rb +92 -464
- data/lib/active_record/connection_adapters/abstract/database_limits.rb +5 -51
- data/lib/active_record/connection_adapters/abstract/database_statements.rb +209 -164
- data/lib/active_record/connection_adapters/abstract/query_cache.rb +38 -22
- data/lib/active_record/connection_adapters/abstract/quoting.rb +103 -82
- data/lib/active_record/connection_adapters/abstract/savepoints.rb +3 -3
- data/lib/active_record/connection_adapters/abstract/schema_creation.rb +140 -110
- data/lib/active_record/connection_adapters/abstract/schema_definitions.rb +236 -94
- data/lib/active_record/connection_adapters/abstract/schema_dumper.rb +16 -5
- data/lib/active_record/connection_adapters/abstract/schema_statements.rb +456 -159
- data/lib/active_record/connection_adapters/abstract/transaction.rb +169 -78
- data/lib/active_record/connection_adapters/abstract_adapter.rb +367 -162
- data/lib/active_record/connection_adapters/abstract_mysql_adapter.rb +311 -327
- data/lib/active_record/connection_adapters/column.rb +33 -11
- data/lib/active_record/connection_adapters/deduplicable.rb +29 -0
- data/lib/active_record/connection_adapters/legacy_pool_manager.rb +35 -0
- data/lib/active_record/connection_adapters/mysql/column.rb +1 -1
- data/lib/active_record/connection_adapters/mysql/database_statements.rb +113 -45
- data/lib/active_record/connection_adapters/mysql/explain_pretty_printer.rb +1 -2
- data/lib/active_record/connection_adapters/mysql/quoting.rb +71 -5
- data/lib/active_record/connection_adapters/mysql/schema_creation.rb +34 -10
- data/lib/active_record/connection_adapters/mysql/schema_definitions.rb +48 -32
- data/lib/active_record/connection_adapters/mysql/schema_dumper.rb +25 -8
- data/lib/active_record/connection_adapters/mysql/schema_statements.rb +143 -19
- data/lib/active_record/connection_adapters/mysql/type_metadata.rb +14 -9
- data/lib/active_record/connection_adapters/mysql2_adapter.rb +63 -22
- data/lib/active_record/connection_adapters/pool_config.rb +73 -0
- data/lib/active_record/connection_adapters/pool_manager.rb +47 -0
- data/lib/active_record/connection_adapters/postgresql/column.rb +53 -28
- data/lib/active_record/connection_adapters/postgresql/database_statements.rb +56 -63
- data/lib/active_record/connection_adapters/postgresql/oid/array.rb +1 -2
- data/lib/active_record/connection_adapters/postgresql/oid/bit.rb +1 -4
- data/lib/active_record/connection_adapters/postgresql/oid/cidr.rb +3 -5
- data/lib/active_record/connection_adapters/postgresql/oid/date.rb +10 -2
- data/lib/active_record/connection_adapters/postgresql/oid/date_time.rb +15 -2
- data/lib/active_record/connection_adapters/postgresql/oid/enum.rb +0 -1
- data/lib/active_record/connection_adapters/postgresql/oid/hstore.rb +54 -16
- data/lib/active_record/connection_adapters/postgresql/oid/interval.rb +49 -0
- data/lib/active_record/connection_adapters/postgresql/oid/legacy_point.rb +3 -4
- data/lib/active_record/connection_adapters/postgresql/oid/macaddr.rb +25 -0
- data/lib/active_record/connection_adapters/postgresql/oid/oid.rb +1 -1
- data/lib/active_record/connection_adapters/postgresql/oid/point.rb +3 -4
- data/lib/active_record/connection_adapters/postgresql/oid/range.rb +25 -7
- data/lib/active_record/connection_adapters/postgresql/oid/specialized_string.rb +1 -1
- data/lib/active_record/connection_adapters/postgresql/oid/timestamp.rb +15 -0
- data/lib/active_record/connection_adapters/postgresql/oid/timestamp_with_time_zone.rb +30 -0
- data/lib/active_record/connection_adapters/postgresql/oid/type_map_initializer.rb +26 -12
- data/lib/active_record/connection_adapters/postgresql/oid/uuid.rb +15 -3
- data/lib/active_record/connection_adapters/postgresql/oid.rb +4 -0
- data/lib/active_record/connection_adapters/postgresql/quoting.rb +89 -52
- data/lib/active_record/connection_adapters/postgresql/referential_integrity.rb +34 -2
- data/lib/active_record/connection_adapters/postgresql/schema_creation.rb +39 -4
- data/lib/active_record/connection_adapters/postgresql/schema_definitions.rb +128 -91
- data/lib/active_record/connection_adapters/postgresql/schema_dumper.rb +25 -1
- data/lib/active_record/connection_adapters/postgresql/schema_statements.rb +149 -113
- data/lib/active_record/connection_adapters/postgresql/type_metadata.rb +31 -26
- data/lib/active_record/connection_adapters/postgresql/utils.rb +0 -1
- data/lib/active_record/connection_adapters/postgresql_adapter.rb +386 -182
- data/lib/active_record/connection_adapters/schema_cache.rb +161 -22
- data/lib/active_record/connection_adapters/sql_type_metadata.rb +17 -6
- data/lib/active_record/connection_adapters/sqlite3/database_statements.rb +152 -0
- data/lib/active_record/connection_adapters/sqlite3/quoting.rb +65 -18
- data/lib/active_record/connection_adapters/sqlite3/schema_creation.rb +5 -1
- data/lib/active_record/connection_adapters/sqlite3/schema_statements.rb +92 -26
- data/lib/active_record/connection_adapters/sqlite3_adapter.rb +251 -204
- data/lib/active_record/connection_adapters/statement_pool.rb +0 -1
- data/lib/active_record/connection_adapters.rb +53 -0
- data/lib/active_record/connection_handling.rb +292 -38
- data/lib/active_record/core.rb +385 -158
- data/lib/active_record/counter_cache.rb +8 -30
- data/lib/active_record/database_configurations/connection_url_resolver.rb +100 -0
- data/lib/active_record/database_configurations/database_config.rb +83 -0
- data/lib/active_record/database_configurations/hash_config.rb +154 -0
- data/lib/active_record/database_configurations/url_config.rb +53 -0
- data/lib/active_record/database_configurations.rb +256 -0
- data/lib/active_record/delegated_type.rb +250 -0
- data/lib/active_record/destroy_association_async_job.rb +36 -0
- data/lib/active_record/disable_joins_association_relation.rb +39 -0
- data/lib/active_record/dynamic_matchers.rb +4 -5
- data/lib/active_record/encryption/cipher/aes256_gcm.rb +98 -0
- data/lib/active_record/encryption/cipher.rb +53 -0
- data/lib/active_record/encryption/config.rb +44 -0
- data/lib/active_record/encryption/configurable.rb +61 -0
- data/lib/active_record/encryption/context.rb +35 -0
- data/lib/active_record/encryption/contexts.rb +72 -0
- data/lib/active_record/encryption/derived_secret_key_provider.rb +12 -0
- data/lib/active_record/encryption/deterministic_key_provider.rb +14 -0
- data/lib/active_record/encryption/encryptable_record.rb +208 -0
- data/lib/active_record/encryption/encrypted_attribute_type.rb +140 -0
- data/lib/active_record/encryption/encrypted_fixtures.rb +38 -0
- data/lib/active_record/encryption/encrypting_only_encryptor.rb +12 -0
- data/lib/active_record/encryption/encryptor.rb +155 -0
- data/lib/active_record/encryption/envelope_encryption_key_provider.rb +55 -0
- data/lib/active_record/encryption/errors.rb +15 -0
- data/lib/active_record/encryption/extended_deterministic_queries.rb +160 -0
- data/lib/active_record/encryption/extended_deterministic_uniqueness_validator.rb +28 -0
- data/lib/active_record/encryption/key.rb +28 -0
- data/lib/active_record/encryption/key_generator.rb +42 -0
- data/lib/active_record/encryption/key_provider.rb +46 -0
- data/lib/active_record/encryption/message.rb +33 -0
- data/lib/active_record/encryption/message_serializer.rb +90 -0
- data/lib/active_record/encryption/null_encryptor.rb +21 -0
- data/lib/active_record/encryption/properties.rb +76 -0
- data/lib/active_record/encryption/read_only_null_encryptor.rb +24 -0
- data/lib/active_record/encryption/scheme.rb +99 -0
- data/lib/active_record/encryption.rb +55 -0
- data/lib/active_record/enum.rb +130 -51
- data/lib/active_record/errors.rb +129 -23
- data/lib/active_record/explain.rb +10 -6
- data/lib/active_record/explain_registry.rb +11 -6
- data/lib/active_record/explain_subscriber.rb +1 -1
- data/lib/active_record/fixture_set/file.rb +22 -15
- data/lib/active_record/fixture_set/model_metadata.rb +32 -0
- data/lib/active_record/fixture_set/render_context.rb +17 -0
- data/lib/active_record/fixture_set/table_row.rb +187 -0
- data/lib/active_record/fixture_set/table_rows.rb +46 -0
- data/lib/active_record/fixtures.rb +206 -490
- data/lib/active_record/future_result.rb +139 -0
- data/lib/active_record/gem_version.rb +3 -3
- data/lib/active_record/inheritance.rb +104 -37
- data/lib/active_record/insert_all.rb +278 -0
- data/lib/active_record/integration.rb +69 -18
- data/lib/active_record/internal_metadata.rb +24 -9
- data/lib/active_record/legacy_yaml_adapter.rb +3 -36
- data/lib/active_record/locking/optimistic.rb +41 -26
- data/lib/active_record/locking/pessimistic.rb +18 -8
- data/lib/active_record/log_subscriber.rb +46 -35
- data/lib/active_record/middleware/database_selector/resolver/session.rb +48 -0
- data/lib/active_record/middleware/database_selector/resolver.rb +88 -0
- data/lib/active_record/middleware/database_selector.rb +82 -0
- data/lib/active_record/middleware/shard_selector.rb +60 -0
- data/lib/active_record/migration/command_recorder.rb +96 -44
- data/lib/active_record/migration/compatibility.rb +246 -64
- data/lib/active_record/migration/join_table.rb +1 -2
- data/lib/active_record/migration.rb +266 -187
- data/lib/active_record/model_schema.rb +165 -52
- data/lib/active_record/nested_attributes.rb +17 -19
- data/lib/active_record/no_touching.rb +11 -4
- data/lib/active_record/null_relation.rb +2 -7
- data/lib/active_record/persistence.rb +467 -92
- data/lib/active_record/query_cache.rb +21 -4
- data/lib/active_record/query_logs.rb +138 -0
- data/lib/active_record/querying.rb +51 -24
- data/lib/active_record/railtie.rb +224 -57
- data/lib/active_record/railties/console_sandbox.rb +2 -4
- data/lib/active_record/railties/controller_runtime.rb +31 -36
- data/lib/active_record/railties/databases.rake +369 -101
- data/lib/active_record/readonly_attributes.rb +15 -0
- data/lib/active_record/reflection.rb +170 -137
- data/lib/active_record/relation/batches/batch_enumerator.rb +44 -14
- data/lib/active_record/relation/batches.rb +46 -37
- data/lib/active_record/relation/calculations.rb +168 -96
- data/lib/active_record/relation/delegation.rb +37 -52
- data/lib/active_record/relation/finder_methods.rb +79 -58
- data/lib/active_record/relation/from_clause.rb +5 -1
- data/lib/active_record/relation/merger.rb +50 -51
- data/lib/active_record/relation/predicate_builder/array_handler.rb +13 -13
- data/lib/active_record/relation/predicate_builder/association_query_value.rb +5 -9
- data/lib/active_record/relation/predicate_builder/basic_object_handler.rb +1 -2
- data/lib/active_record/relation/predicate_builder/polymorphic_array_value.rb +11 -10
- data/lib/active_record/relation/predicate_builder/range_handler.rb +3 -23
- data/lib/active_record/relation/predicate_builder/relation_handler.rb +1 -1
- data/lib/active_record/relation/predicate_builder.rb +58 -46
- data/lib/active_record/relation/query_attribute.rb +9 -10
- data/lib/active_record/relation/query_methods.rb +685 -208
- data/lib/active_record/relation/record_fetch_warning.rb +9 -11
- data/lib/active_record/relation/spawn_methods.rb +10 -10
- data/lib/active_record/relation/where_clause.rb +108 -64
- data/lib/active_record/relation.rb +515 -151
- data/lib/active_record/result.rb +78 -42
- data/lib/active_record/runtime_registry.rb +9 -13
- data/lib/active_record/sanitization.rb +29 -44
- data/lib/active_record/schema.rb +37 -31
- data/lib/active_record/schema_dumper.rb +74 -23
- data/lib/active_record/schema_migration.rb +7 -9
- data/lib/active_record/scoping/default.rb +62 -17
- data/lib/active_record/scoping/named.rb +17 -32
- data/lib/active_record/scoping.rb +70 -41
- data/lib/active_record/secure_token.rb +16 -8
- data/lib/active_record/serialization.rb +6 -4
- data/lib/active_record/signed_id.rb +116 -0
- data/lib/active_record/statement_cache.rb +49 -6
- data/lib/active_record/store.rb +88 -9
- data/lib/active_record/suppressor.rb +13 -17
- data/lib/active_record/table_metadata.rb +42 -43
- data/lib/active_record/tasks/database_tasks.rb +352 -94
- data/lib/active_record/tasks/mysql_database_tasks.rb +37 -39
- data/lib/active_record/tasks/postgresql_database_tasks.rb +41 -39
- data/lib/active_record/tasks/sqlite_database_tasks.rb +14 -17
- data/lib/active_record/test_databases.rb +24 -0
- data/lib/active_record/test_fixtures.rb +287 -0
- data/lib/active_record/timestamp.rb +44 -34
- data/lib/active_record/touch_later.rb +23 -22
- data/lib/active_record/transactions.rb +67 -128
- data/lib/active_record/translation.rb +3 -3
- data/lib/active_record/type/adapter_specific_registry.rb +34 -19
- data/lib/active_record/type/hash_lookup_type_map.rb +34 -2
- data/lib/active_record/type/internal/timezone.rb +2 -2
- data/lib/active_record/type/serialized.rb +7 -4
- data/lib/active_record/type/time.rb +10 -0
- data/lib/active_record/type/type_map.rb +17 -21
- data/lib/active_record/type/unsigned_integer.rb +0 -1
- data/lib/active_record/type.rb +9 -5
- data/lib/active_record/type_caster/connection.rb +15 -15
- data/lib/active_record/type_caster/map.rb +8 -8
- data/lib/active_record/validations/associated.rb +2 -3
- data/lib/active_record/validations/numericality.rb +35 -0
- data/lib/active_record/validations/uniqueness.rb +39 -31
- data/lib/active_record/validations.rb +4 -3
- data/lib/active_record.rb +209 -32
- data/lib/arel/alias_predication.rb +9 -0
- data/lib/arel/attributes/attribute.rb +33 -0
- data/lib/arel/collectors/bind.rb +29 -0
- data/lib/arel/collectors/composite.rb +39 -0
- data/lib/arel/collectors/plain_string.rb +20 -0
- data/lib/arel/collectors/sql_string.rb +27 -0
- data/lib/arel/collectors/substitute_binds.rb +35 -0
- data/lib/arel/crud.rb +48 -0
- data/lib/arel/delete_manager.rb +32 -0
- data/lib/arel/errors.rb +9 -0
- data/lib/arel/expressions.rb +29 -0
- data/lib/arel/factory_methods.rb +49 -0
- data/lib/arel/filter_predications.rb +9 -0
- data/lib/arel/insert_manager.rb +48 -0
- data/lib/arel/math.rb +45 -0
- data/lib/arel/nodes/and.rb +32 -0
- data/lib/arel/nodes/ascending.rb +23 -0
- data/lib/arel/nodes/binary.rb +126 -0
- data/lib/arel/nodes/bind_param.rb +44 -0
- data/lib/arel/nodes/case.rb +55 -0
- data/lib/arel/nodes/casted.rb +62 -0
- data/lib/arel/nodes/comment.rb +29 -0
- data/lib/arel/nodes/count.rb +12 -0
- data/lib/arel/nodes/delete_statement.rb +44 -0
- data/lib/arel/nodes/descending.rb +23 -0
- data/lib/arel/nodes/equality.rb +15 -0
- data/lib/arel/nodes/extract.rb +24 -0
- data/lib/arel/nodes/false.rb +16 -0
- data/lib/arel/nodes/filter.rb +10 -0
- data/lib/arel/nodes/full_outer_join.rb +8 -0
- data/lib/arel/nodes/function.rb +45 -0
- data/lib/arel/nodes/grouping.rb +11 -0
- data/lib/arel/nodes/homogeneous_in.rb +76 -0
- data/lib/arel/nodes/in.rb +15 -0
- data/lib/arel/nodes/infix_operation.rb +92 -0
- data/lib/arel/nodes/inner_join.rb +8 -0
- data/lib/arel/nodes/insert_statement.rb +37 -0
- data/lib/arel/nodes/join_source.rb +20 -0
- data/lib/arel/nodes/matches.rb +18 -0
- data/lib/arel/nodes/named_function.rb +23 -0
- data/lib/arel/nodes/node.rb +51 -0
- data/lib/arel/nodes/node_expression.rb +13 -0
- data/lib/arel/nodes/ordering.rb +27 -0
- data/lib/arel/nodes/outer_join.rb +8 -0
- data/lib/arel/nodes/over.rb +15 -0
- data/lib/arel/nodes/regexp.rb +16 -0
- data/lib/arel/nodes/right_outer_join.rb +8 -0
- data/lib/arel/nodes/select_core.rb +67 -0
- data/lib/arel/nodes/select_statement.rb +41 -0
- data/lib/arel/nodes/sql_literal.rb +19 -0
- data/lib/arel/nodes/string_join.rb +11 -0
- data/lib/arel/nodes/table_alias.rb +31 -0
- data/lib/arel/nodes/terminal.rb +16 -0
- data/lib/arel/nodes/true.rb +16 -0
- data/lib/arel/nodes/unary.rb +44 -0
- data/lib/arel/nodes/unary_operation.rb +20 -0
- data/lib/arel/nodes/unqualified_column.rb +22 -0
- data/lib/arel/nodes/update_statement.rb +46 -0
- data/lib/arel/nodes/values_list.rb +9 -0
- data/lib/arel/nodes/window.rb +126 -0
- data/lib/arel/nodes/with.rb +11 -0
- data/lib/arel/nodes.rb +71 -0
- data/lib/arel/order_predications.rb +13 -0
- data/lib/arel/predications.rb +258 -0
- data/lib/arel/select_manager.rb +276 -0
- data/lib/arel/table.rb +117 -0
- data/lib/arel/tree_manager.rb +60 -0
- data/lib/arel/update_manager.rb +48 -0
- data/lib/arel/visitors/dot.rb +298 -0
- data/lib/arel/visitors/mysql.rb +99 -0
- data/lib/arel/visitors/postgresql.rb +110 -0
- data/lib/arel/visitors/sqlite.rb +38 -0
- data/lib/arel/visitors/to_sql.rb +955 -0
- data/lib/arel/visitors/visitor.rb +45 -0
- data/lib/arel/visitors.rb +13 -0
- data/lib/arel/window_predications.rb +9 -0
- data/lib/arel.rb +55 -0
- data/lib/rails/generators/active_record/application_record/application_record_generator.rb +0 -1
- data/lib/rails/generators/active_record/application_record/templates/application_record.rb.tt +1 -1
- data/lib/rails/generators/active_record/migration/migration_generator.rb +3 -5
- data/lib/rails/generators/active_record/migration/templates/create_table_migration.rb.tt +3 -1
- data/lib/rails/generators/active_record/migration/templates/migration.rb.tt +7 -5
- data/lib/rails/generators/active_record/migration.rb +19 -2
- data/lib/rails/generators/active_record/model/model_generator.rb +39 -2
- data/lib/rails/generators/active_record/model/templates/abstract_base_class.rb.tt +7 -0
- data/lib/rails/generators/active_record/model/templates/model.rb.tt +10 -1
- data/lib/rails/generators/active_record/model/templates/module.rb.tt +2 -2
- data/lib/rails/generators/active_record/multi_db/multi_db_generator.rb +16 -0
- data/lib/rails/generators/active_record/multi_db/templates/multi_db.rb.tt +44 -0
- metadata +162 -32
- data/lib/active_record/attribute_decorators.rb +0 -90
- data/lib/active_record/collection_cache_key.rb +0 -53
- data/lib/active_record/connection_adapters/connection_specification.rb +0 -287
- data/lib/active_record/connection_adapters/determine_if_preparable_visitor.rb +0 -33
- data/lib/active_record/define_callbacks.rb +0 -22
- data/lib/active_record/relation/predicate_builder/base_handler.rb +0 -19
- data/lib/active_record/relation/where_clause_factory.rb +0 -34
@@ -7,7 +7,7 @@ module ActiveRecord
|
|
7
7
|
module PostgreSQL
|
8
8
|
module OID # :nodoc:
|
9
9
|
class Point < Type::Value # :nodoc:
|
10
|
-
include Type::Helpers::Mutable
|
10
|
+
include ActiveModel::Type::Helpers::Mutable
|
11
11
|
|
12
12
|
def type
|
13
13
|
:point
|
@@ -18,7 +18,7 @@ module ActiveRecord
|
|
18
18
|
when ::String
|
19
19
|
return if value.blank?
|
20
20
|
|
21
|
-
if value
|
21
|
+
if value.start_with?("(") && value.end_with?(")")
|
22
22
|
value = value[1...-1]
|
23
23
|
end
|
24
24
|
x, y = value.split(",")
|
@@ -50,9 +50,8 @@ module ActiveRecord
|
|
50
50
|
end
|
51
51
|
|
52
52
|
private
|
53
|
-
|
54
53
|
def number_for_point(number)
|
55
|
-
number.to_s.
|
54
|
+
number.to_s.delete_suffix(".0")
|
56
55
|
end
|
57
56
|
|
58
57
|
def build_point(x, y)
|
@@ -58,25 +58,43 @@ module ActiveRecord
|
|
58
58
|
end
|
59
59
|
|
60
60
|
private
|
61
|
-
|
62
61
|
def type_cast_single(value)
|
63
62
|
infinity?(value) ? value : @subtype.deserialize(value)
|
64
63
|
end
|
65
64
|
|
66
65
|
def type_cast_single_for_database(value)
|
67
|
-
infinity?(value) ? value : @subtype.serialize(value)
|
66
|
+
infinity?(value) ? value : @subtype.serialize(@subtype.cast(value))
|
68
67
|
end
|
69
68
|
|
70
69
|
def extract_bounds(value)
|
71
|
-
from, to = value[1..-2].split(",")
|
70
|
+
from, to = value[1..-2].split(",", 2)
|
72
71
|
{
|
73
|
-
from: (
|
74
|
-
to: (
|
75
|
-
exclude_start: (
|
76
|
-
exclude_end: (
|
72
|
+
from: (from == "" || from == "-infinity") ? infinity(negative: true) : unquote(from),
|
73
|
+
to: (to == "" || to == "infinity") ? infinity : unquote(to),
|
74
|
+
exclude_start: value.start_with?("("),
|
75
|
+
exclude_end: value.end_with?(")")
|
77
76
|
}
|
78
77
|
end
|
79
78
|
|
79
|
+
# When formatting the bound values of range types, PostgreSQL quotes
|
80
|
+
# the bound value using double-quotes in certain conditions. Within
|
81
|
+
# a double-quoted string, literal " and \ characters are themselves
|
82
|
+
# escaped. In input, PostgreSQL accepts multiple escape styles for "
|
83
|
+
# (either \" or "") but in output always uses "".
|
84
|
+
# See:
|
85
|
+
# * https://www.postgresql.org/docs/current/rangetypes.html#RANGETYPES-IO
|
86
|
+
# * https://www.postgresql.org/docs/current/rowtypes.html#ROWTYPES-IO-SYNTAX
|
87
|
+
def unquote(value)
|
88
|
+
if value.start_with?('"') && value.end_with?('"')
|
89
|
+
unquoted_value = value[1..-2]
|
90
|
+
unquoted_value.gsub!('""', '"')
|
91
|
+
unquoted_value.gsub!("\\\\", "\\")
|
92
|
+
unquoted_value
|
93
|
+
else
|
94
|
+
value
|
95
|
+
end
|
96
|
+
end
|
97
|
+
|
80
98
|
def infinity(negative: false)
|
81
99
|
if subtype.respond_to?(:infinity)
|
82
100
|
subtype.infinity(negative: negative)
|
@@ -0,0 +1,15 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module ActiveRecord
|
4
|
+
module ConnectionAdapters
|
5
|
+
module PostgreSQL
|
6
|
+
module OID # :nodoc:
|
7
|
+
class Timestamp < DateTime # :nodoc:
|
8
|
+
def type
|
9
|
+
real_type_unless_aliased(:timestamp)
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module ActiveRecord
|
4
|
+
module ConnectionAdapters
|
5
|
+
module PostgreSQL
|
6
|
+
module OID # :nodoc:
|
7
|
+
class TimestampWithTimeZone < DateTime # :nodoc:
|
8
|
+
def type
|
9
|
+
real_type_unless_aliased(:timestamptz)
|
10
|
+
end
|
11
|
+
|
12
|
+
def cast_value(value)
|
13
|
+
return if value.blank?
|
14
|
+
|
15
|
+
time = super
|
16
|
+
return time if time.is_a?(ActiveSupport::TimeWithZone)
|
17
|
+
|
18
|
+
# While in UTC mode, the PG gem may not return times back in "UTC" even if they were provided to Postgres in UTC.
|
19
|
+
# We prefer times always in UTC, so here we convert back.
|
20
|
+
if is_utc?
|
21
|
+
time.getutc
|
22
|
+
else
|
23
|
+
time.getlocal
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
@@ -1,5 +1,7 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
+
require "active_support/core_ext/array/extract"
|
4
|
+
|
3
5
|
module ActiveRecord
|
4
6
|
module ConnectionAdapters
|
5
7
|
module PostgreSQL
|
@@ -16,12 +18,12 @@ module ActiveRecord
|
|
16
18
|
|
17
19
|
def run(records)
|
18
20
|
nodes = records.reject { |row| @store.key? row["oid"].to_i }
|
19
|
-
mapped
|
20
|
-
ranges
|
21
|
-
enums
|
22
|
-
domains
|
23
|
-
arrays
|
24
|
-
composites
|
21
|
+
mapped = nodes.extract! { |row| @store.key? row["typname"] }
|
22
|
+
ranges = nodes.extract! { |row| row["typtype"] == "r" }
|
23
|
+
enums = nodes.extract! { |row| row["typtype"] == "e" }
|
24
|
+
domains = nodes.extract! { |row| row["typtype"] == "d" }
|
25
|
+
arrays = nodes.extract! { |row| row["typinput"] == "array_in" }
|
26
|
+
composites = nodes.extract! { |row| row["typelem"].to_i != 0 }
|
25
27
|
|
26
28
|
mapped.each { |row| register_mapped_type(row) }
|
27
29
|
enums.each { |row| register_enum_type(row) }
|
@@ -31,15 +33,27 @@ module ActiveRecord
|
|
31
33
|
composites.each { |row| register_composite_type(row) }
|
32
34
|
end
|
33
35
|
|
34
|
-
def
|
36
|
+
def query_conditions_for_known_type_names
|
35
37
|
known_type_names = @store.keys.map { |n| "'#{n}'" }
|
36
|
-
|
37
|
-
<<-SQL % [known_type_names.join(", "), known_type_types.join(", ")]
|
38
|
+
<<~SQL % known_type_names.join(", ")
|
38
39
|
WHERE
|
39
40
|
t.typname IN (%s)
|
40
|
-
|
41
|
-
|
42
|
-
|
41
|
+
SQL
|
42
|
+
end
|
43
|
+
|
44
|
+
def query_conditions_for_known_type_types
|
45
|
+
known_type_types = %w('r' 'e' 'd')
|
46
|
+
<<~SQL % known_type_types.join(", ")
|
47
|
+
WHERE
|
48
|
+
t.typtype IN (%s)
|
49
|
+
SQL
|
50
|
+
end
|
51
|
+
|
52
|
+
def query_conditions_for_array_types
|
53
|
+
known_type_oids = @store.keys.reject { |k| k.is_a?(String) }
|
54
|
+
<<~SQL % [known_type_oids.join(", ")]
|
55
|
+
WHERE
|
56
|
+
t.typelem IN (%s)
|
43
57
|
SQL
|
44
58
|
end
|
45
59
|
|
@@ -7,15 +7,27 @@ module ActiveRecord
|
|
7
7
|
class Uuid < Type::Value # :nodoc:
|
8
8
|
ACCEPTABLE_UUID = %r{\A(\{)?([a-fA-F0-9]{4}-?){8}(?(1)\}|)\z}
|
9
9
|
|
10
|
-
|
10
|
+
alias :serialize :deserialize
|
11
11
|
|
12
12
|
def type
|
13
13
|
:uuid
|
14
14
|
end
|
15
15
|
|
16
|
-
def
|
17
|
-
|
16
|
+
def changed?(old_value, new_value, _new_value_before_type_cast)
|
17
|
+
old_value.class != new_value.class ||
|
18
|
+
new_value && old_value.casecmp(new_value) != 0
|
18
19
|
end
|
20
|
+
|
21
|
+
def changed_in_place?(raw_old_value, new_value)
|
22
|
+
raw_old_value.class != new_value.class ||
|
23
|
+
new_value && raw_old_value.casecmp(new_value) != 0
|
24
|
+
end
|
25
|
+
|
26
|
+
private
|
27
|
+
def cast_value(value)
|
28
|
+
casted = value.to_s
|
29
|
+
casted if casted.match?(ACCEPTABLE_UUID)
|
30
|
+
end
|
19
31
|
end
|
20
32
|
end
|
21
33
|
end
|
@@ -11,13 +11,17 @@ require "active_record/connection_adapters/postgresql/oid/decimal"
|
|
11
11
|
require "active_record/connection_adapters/postgresql/oid/enum"
|
12
12
|
require "active_record/connection_adapters/postgresql/oid/hstore"
|
13
13
|
require "active_record/connection_adapters/postgresql/oid/inet"
|
14
|
+
require "active_record/connection_adapters/postgresql/oid/interval"
|
14
15
|
require "active_record/connection_adapters/postgresql/oid/jsonb"
|
16
|
+
require "active_record/connection_adapters/postgresql/oid/macaddr"
|
15
17
|
require "active_record/connection_adapters/postgresql/oid/money"
|
16
18
|
require "active_record/connection_adapters/postgresql/oid/oid"
|
17
19
|
require "active_record/connection_adapters/postgresql/oid/point"
|
18
20
|
require "active_record/connection_adapters/postgresql/oid/legacy_point"
|
19
21
|
require "active_record/connection_adapters/postgresql/oid/range"
|
20
22
|
require "active_record/connection_adapters/postgresql/oid/specialized_string"
|
23
|
+
require "active_record/connection_adapters/postgresql/oid/timestamp"
|
24
|
+
require "active_record/connection_adapters/postgresql/oid/timestamp_with_time_zone"
|
21
25
|
require "active_record/connection_adapters/postgresql/oid/uuid"
|
22
26
|
require "active_record/connection_adapters/postgresql/oid/vector"
|
23
27
|
require "active_record/connection_adapters/postgresql/oid/xml"
|
@@ -16,9 +16,34 @@ module ActiveRecord
|
|
16
16
|
@connection.unescape_bytea(value) if value
|
17
17
|
end
|
18
18
|
|
19
|
+
def quote(value) # :nodoc:
|
20
|
+
case value
|
21
|
+
when OID::Xml::Data
|
22
|
+
"xml '#{quote_string(value.to_s)}'"
|
23
|
+
when OID::Bit::Data
|
24
|
+
if value.binary?
|
25
|
+
"B'#{value}'"
|
26
|
+
elsif value.hex?
|
27
|
+
"X'#{value}'"
|
28
|
+
end
|
29
|
+
when Numeric
|
30
|
+
if value.finite?
|
31
|
+
super
|
32
|
+
else
|
33
|
+
"'#{value}'"
|
34
|
+
end
|
35
|
+
when OID::Array::Data
|
36
|
+
quote(encode_array(value))
|
37
|
+
when Range
|
38
|
+
quote(encode_range(value))
|
39
|
+
else
|
40
|
+
super
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
19
44
|
# Quotes strings for use in SQL input.
|
20
|
-
def quote_string(s)
|
21
|
-
|
45
|
+
def quote_string(s) # :nodoc:
|
46
|
+
PG::Connection.escape(s)
|
22
47
|
end
|
23
48
|
|
24
49
|
# Checks the following cases:
|
@@ -30,7 +55,7 @@ module ActiveRecord
|
|
30
55
|
# - "schema.name".table_name
|
31
56
|
# - "schema.name"."table.name"
|
32
57
|
def quote_table_name(name) # :nodoc:
|
33
|
-
|
58
|
+
self.class.quoted_table_names[name] ||= Utils.extract_schema_qualified_name(name.to_s).quoted.freeze
|
34
59
|
end
|
35
60
|
|
36
61
|
# Quotes schema names for use in SQL queries.
|
@@ -44,11 +69,11 @@ module ActiveRecord
|
|
44
69
|
|
45
70
|
# Quotes column names for use in SQL queries.
|
46
71
|
def quote_column_name(name) # :nodoc:
|
47
|
-
|
72
|
+
self.class.quoted_column_names[name] ||= PG::Connection.quote_ident(super).freeze
|
48
73
|
end
|
49
74
|
|
50
75
|
# Quote date/time values for use in SQL input.
|
51
|
-
def quoted_date(value)
|
76
|
+
def quoted_date(value) # :nodoc:
|
52
77
|
if value.year <= 0
|
53
78
|
bce_year = format("%04d", -value.year + 1)
|
54
79
|
super.sub(/^-?\d+/, bce_year) + " BC"
|
@@ -67,8 +92,26 @@ module ActiveRecord
|
|
67
92
|
elsif column.type == :uuid && value.is_a?(String) && /\(\)/.match?(value)
|
68
93
|
value # Does not quote function default values for UUID columns
|
69
94
|
elsif column.respond_to?(:array?)
|
70
|
-
|
71
|
-
quote(value)
|
95
|
+
type = lookup_cast_type_from_column(column)
|
96
|
+
quote(type.serialize(value))
|
97
|
+
else
|
98
|
+
super
|
99
|
+
end
|
100
|
+
end
|
101
|
+
|
102
|
+
def type_cast(value) # :nodoc:
|
103
|
+
case value
|
104
|
+
when Type::Binary::Data
|
105
|
+
# Return a bind param hash with format as binary.
|
106
|
+
# See https://deveiate.org/code/pg/PG/Connection.html#method-i-exec_prepared-doc
|
107
|
+
# for more information
|
108
|
+
{ value: value.to_s, format: 1 }
|
109
|
+
when OID::Xml::Data, OID::Bit::Data
|
110
|
+
value.to_s
|
111
|
+
when OID::Array::Data
|
112
|
+
encode_array(value)
|
113
|
+
when Range
|
114
|
+
encode_range(value)
|
72
115
|
else
|
73
116
|
super
|
74
117
|
end
|
@@ -78,54 +121,48 @@ module ActiveRecord
|
|
78
121
|
type_map.lookup(column.oid, column.fmod, column.sql_type)
|
79
122
|
end
|
80
123
|
|
124
|
+
def column_name_matcher
|
125
|
+
COLUMN_NAME
|
126
|
+
end
|
127
|
+
|
128
|
+
def column_name_with_order_matcher
|
129
|
+
COLUMN_NAME_WITH_ORDER
|
130
|
+
end
|
131
|
+
|
132
|
+
COLUMN_NAME = /
|
133
|
+
\A
|
134
|
+
(
|
135
|
+
(?:
|
136
|
+
# "schema_name"."table_name"."column_name"::type_name | function(one or no argument)::type_name
|
137
|
+
((?:\w+\.|"\w+"\.){,2}(?:\w+|"\w+")(?:::\w+)?) | \w+\((?:|\g<2>)\)(?:::\w+)?
|
138
|
+
)
|
139
|
+
(?:(?:\s+AS)?\s+(?:\w+|"\w+"))?
|
140
|
+
)
|
141
|
+
(?:\s*,\s*\g<1>)*
|
142
|
+
\z
|
143
|
+
/ix
|
144
|
+
|
145
|
+
COLUMN_NAME_WITH_ORDER = /
|
146
|
+
\A
|
147
|
+
(
|
148
|
+
(?:
|
149
|
+
# "schema_name"."table_name"."column_name"::type_name | function(one or no argument)::type_name
|
150
|
+
((?:\w+\.|"\w+"\.){,2}(?:\w+|"\w+")(?:::\w+)?) | \w+\((?:|\g<2>)\)(?:::\w+)?
|
151
|
+
)
|
152
|
+
(?:\s+ASC|\s+DESC)?
|
153
|
+
(?:\s+NULLS\s+(?:FIRST|LAST))?
|
154
|
+
)
|
155
|
+
(?:\s*,\s*\g<1>)*
|
156
|
+
\z
|
157
|
+
/ix
|
158
|
+
|
159
|
+
private_constant :COLUMN_NAME, :COLUMN_NAME_WITH_ORDER
|
160
|
+
|
81
161
|
private
|
82
162
|
def lookup_cast_type(sql_type)
|
83
163
|
super(query_value("SELECT #{quote(sql_type)}::regtype::oid", "SCHEMA").to_i)
|
84
164
|
end
|
85
165
|
|
86
|
-
def _quote(value)
|
87
|
-
case value
|
88
|
-
when OID::Xml::Data
|
89
|
-
"xml '#{quote_string(value.to_s)}'"
|
90
|
-
when OID::Bit::Data
|
91
|
-
if value.binary?
|
92
|
-
"B'#{value}'"
|
93
|
-
elsif value.hex?
|
94
|
-
"X'#{value}'"
|
95
|
-
end
|
96
|
-
when Float
|
97
|
-
if value.infinite? || value.nan?
|
98
|
-
"'#{value}'"
|
99
|
-
else
|
100
|
-
super
|
101
|
-
end
|
102
|
-
when OID::Array::Data
|
103
|
-
_quote(encode_array(value))
|
104
|
-
when Range
|
105
|
-
_quote(encode_range(value))
|
106
|
-
else
|
107
|
-
super
|
108
|
-
end
|
109
|
-
end
|
110
|
-
|
111
|
-
def _type_cast(value)
|
112
|
-
case value
|
113
|
-
when Type::Binary::Data
|
114
|
-
# Return a bind param hash with format as binary.
|
115
|
-
# See https://deveiate.org/code/pg/PG/Connection.html#method-i-exec_prepared-doc
|
116
|
-
# for more information
|
117
|
-
{ value: value.to_s, format: 1 }
|
118
|
-
when OID::Xml::Data, OID::Bit::Data
|
119
|
-
value.to_s
|
120
|
-
when OID::Array::Data
|
121
|
-
encode_array(value)
|
122
|
-
when Range
|
123
|
-
encode_range(value)
|
124
|
-
else
|
125
|
-
super
|
126
|
-
end
|
127
|
-
end
|
128
|
-
|
129
166
|
def encode_array(array_data)
|
130
167
|
encoder = array_data.encoder
|
131
168
|
values = type_cast_array(array_data.values)
|
@@ -138,7 +175,7 @@ module ActiveRecord
|
|
138
175
|
end
|
139
176
|
|
140
177
|
def encode_range(range)
|
141
|
-
"[#{type_cast_range_value(range.
|
178
|
+
"[#{type_cast_range_value(range.begin)},#{type_cast_range_value(range.end)}#{range.exclude_end? ? ')' : ']'}"
|
142
179
|
end
|
143
180
|
|
144
181
|
def determine_encoding_of_strings_in_array(value)
|
@@ -151,7 +188,7 @@ module ActiveRecord
|
|
151
188
|
def type_cast_array(values)
|
152
189
|
case values
|
153
190
|
when ::Array then values.map { |item| type_cast_array(item) }
|
154
|
-
else
|
191
|
+
else type_cast(values)
|
155
192
|
end
|
156
193
|
end
|
157
194
|
|
@@ -24,9 +24,9 @@ WARNING: Rails was not able to disable referential integrity.
|
|
24
24
|
This is most likely caused due to missing permissions.
|
25
25
|
Rails needs superuser privileges to disable referential integrity.
|
26
26
|
|
27
|
-
cause: #{original_exception
|
27
|
+
cause: #{original_exception&.message}
|
28
28
|
|
29
|
-
|
29
|
+
WARNING
|
30
30
|
raise e
|
31
31
|
end
|
32
32
|
|
@@ -37,6 +37,38 @@ Rails needs superuser privileges to disable referential integrity.
|
|
37
37
|
rescue ActiveRecord::ActiveRecordError
|
38
38
|
end
|
39
39
|
end
|
40
|
+
|
41
|
+
def all_foreign_keys_valid? # :nodoc:
|
42
|
+
sql = <<~SQL
|
43
|
+
do $$
|
44
|
+
declare r record;
|
45
|
+
BEGIN
|
46
|
+
FOR r IN (
|
47
|
+
SELECT FORMAT(
|
48
|
+
'UPDATE pg_constraint SET convalidated=false WHERE conname = ''%I''; ALTER TABLE %I VALIDATE CONSTRAINT %I;',
|
49
|
+
constraint_name,
|
50
|
+
table_name,
|
51
|
+
constraint_name
|
52
|
+
) AS constraint_check
|
53
|
+
FROM information_schema.table_constraints WHERE constraint_type = 'FOREIGN KEY'
|
54
|
+
)
|
55
|
+
LOOP
|
56
|
+
EXECUTE (r.constraint_check);
|
57
|
+
END LOOP;
|
58
|
+
END;
|
59
|
+
$$;
|
60
|
+
SQL
|
61
|
+
|
62
|
+
begin
|
63
|
+
transaction(requires_new: true) do
|
64
|
+
execute(sql)
|
65
|
+
end
|
66
|
+
|
67
|
+
true
|
68
|
+
rescue ActiveRecord::StatementInvalid
|
69
|
+
false
|
70
|
+
end
|
71
|
+
end
|
40
72
|
end
|
41
73
|
end
|
42
74
|
end
|
@@ -3,13 +3,24 @@
|
|
3
3
|
module ActiveRecord
|
4
4
|
module ConnectionAdapters
|
5
5
|
module PostgreSQL
|
6
|
-
class SchemaCreation <
|
6
|
+
class SchemaCreation < SchemaCreation # :nodoc:
|
7
7
|
private
|
8
8
|
def visit_AlterTable(o)
|
9
9
|
super << o.constraint_validations.map { |fk| visit_ValidateConstraint fk }.join(" ")
|
10
10
|
end
|
11
11
|
|
12
12
|
def visit_AddForeignKey(o)
|
13
|
+
super.dup.tap do |sql|
|
14
|
+
if o.deferrable
|
15
|
+
sql << " DEFERRABLE"
|
16
|
+
sql << " INITIALLY #{o.deferrable.to_s.upcase}" unless o.deferrable == true
|
17
|
+
end
|
18
|
+
|
19
|
+
sql << " NOT VALID" unless o.validate?
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def visit_CheckConstraintDefinition(o)
|
13
24
|
super.dup.tap { |sql| sql << " NOT VALID" unless o.validate? }
|
14
25
|
end
|
15
26
|
|
@@ -19,10 +30,10 @@ module ActiveRecord
|
|
19
30
|
|
20
31
|
def visit_ChangeColumnDefinition(o)
|
21
32
|
column = o.column
|
22
|
-
column.sql_type = type_to_sql(column.type, column.options)
|
33
|
+
column.sql_type = type_to_sql(column.type, **column.options)
|
23
34
|
quoted_column_name = quote_column_name(o.name)
|
24
35
|
|
25
|
-
change_column_sql = "ALTER COLUMN #{quoted_column_name} TYPE #{column.sql_type}"
|
36
|
+
change_column_sql = +"ALTER COLUMN #{quoted_column_name} TYPE #{column.sql_type}"
|
26
37
|
|
27
38
|
options = column_options(column)
|
28
39
|
|
@@ -33,7 +44,7 @@ module ActiveRecord
|
|
33
44
|
if options[:using]
|
34
45
|
change_column_sql << " USING #{options[:using]}"
|
35
46
|
elsif options[:cast_as]
|
36
|
-
cast_as_type = type_to_sql(options[:cast_as], options)
|
47
|
+
cast_as_type = type_to_sql(options[:cast_as], **options)
|
37
48
|
change_column_sql << " USING CAST(#{quoted_column_name} AS #{cast_as_type})"
|
38
49
|
end
|
39
50
|
|
@@ -57,8 +68,32 @@ module ActiveRecord
|
|
57
68
|
if options[:collation]
|
58
69
|
sql << " COLLATE \"#{options[:collation]}\""
|
59
70
|
end
|
71
|
+
|
72
|
+
if as = options[:as]
|
73
|
+
sql << " GENERATED ALWAYS AS (#{as})"
|
74
|
+
|
75
|
+
if options[:stored]
|
76
|
+
sql << " STORED"
|
77
|
+
else
|
78
|
+
raise ArgumentError, <<~MSG
|
79
|
+
PostgreSQL currently does not support VIRTUAL (not persisted) generated columns.
|
80
|
+
Specify 'stored: true' option for '#{options[:column].name}'
|
81
|
+
MSG
|
82
|
+
end
|
83
|
+
end
|
60
84
|
super
|
61
85
|
end
|
86
|
+
|
87
|
+
# Returns any SQL string to go between CREATE and TABLE. May be nil.
|
88
|
+
def table_modifier_in_create(o)
|
89
|
+
# A table cannot be both TEMPORARY and UNLOGGED, since all TEMPORARY
|
90
|
+
# tables are already UNLOGGED.
|
91
|
+
if o.temporary
|
92
|
+
" TEMPORARY"
|
93
|
+
elsif o.unlogged
|
94
|
+
" UNLOGGED"
|
95
|
+
end
|
96
|
+
end
|
62
97
|
end
|
63
98
|
end
|
64
99
|
end
|