diff --git a/django/db/backends/oracle/creation.py b/django/db/backends/oracle/creation.py index 109b97b3f2..98ea186dcb 100644 --- a/django/db/backends/oracle/creation.py +++ b/django/db/backends/oracle/creation.py @@ -187,16 +187,32 @@ class DatabaseCreation(BaseDatabaseCreation): def _execute_test_db_creation(self, cursor, parameters, verbosity, keepdb=False): if verbosity >= 2: self.log('_create_test_db(): dbname = %s' % parameters['user']) - statements = [ - """CREATE TABLESPACE %(tblspace)s - DATAFILE '%(datafile)s' SIZE %(size)s - REUSE AUTOEXTEND ON NEXT %(extsize)s MAXSIZE %(maxsize)s - """, - """CREATE TEMPORARY TABLESPACE %(tblspace_temp)s - TEMPFILE '%(datafile_tmp)s' SIZE %(size_tmp)s - REUSE AUTOEXTEND ON NEXT %(extsize_tmp)s MAXSIZE %(maxsize_tmp)s - """, - ] + if self._test_database_oracle_managed_files(): + statements = [ + """ + CREATE TABLESPACE %(tblspace)s + DATAFILE SIZE %(size)s + AUTOEXTEND ON NEXT %(extsize)s MAXSIZE %(maxsize)s + """, + """ + CREATE TEMPORARY TABLESPACE %(tblspace_temp)s + TEMPFILE SIZE %(size_tmp)s + AUTOEXTEND ON NEXT %(extsize_tmp)s MAXSIZE %(maxsize_tmp)s + """, + ] + else: + statements = [ + """ + CREATE TABLESPACE %(tblspace)s + DATAFILE '%(datafile)s' SIZE %(size)s REUSE + AUTOEXTEND ON NEXT %(extsize)s MAXSIZE %(maxsize)s + """, + """ + CREATE TEMPORARY TABLESPACE %(tblspace_temp)s + TEMPFILE '%(datafile_tmp)s' SIZE %(size_tmp)s REUSE + AUTOEXTEND ON NEXT %(extsize_tmp)s MAXSIZE %(maxsize_tmp)s + """, + ] # Ignore "tablespace already exists" error when keepdb is on. acceptable_ora_err = 'ORA-01543' if keepdb else None self._execute_allow_fail_statements(cursor, statements, parameters, verbosity, acceptable_ora_err) @@ -359,6 +375,9 @@ class DatabaseCreation(BaseDatabaseCreation): def _test_database_tblspace_tmp_extsize(self): return self._test_settings_get('DATAFILE_TMP_EXTSIZE', default='25M') + def _test_database_oracle_managed_files(self): + return self._test_settings_get('ORACLE_MANAGED_FILES', default=False) + def _get_test_db_name(self): """ Return the 'production' DB name to get the test DB creation machinery diff --git a/docs/ref/settings.txt b/docs/ref/settings.txt index a3f6f421dd..40f8a5cf49 100644 --- a/docs/ref/settings.txt +++ b/docs/ref/settings.txt @@ -842,6 +842,20 @@ This is an Oracle-specific setting. The password to use when connecting to the Oracle database that will be used when running tests. If not provided, Django will generate a random password. +.. setting:: TEST_ORACLE_MANAGED_FILES + +``ORACLE_MANAGED_FILES`` +^^^^^^^^^^^^^^^^^^^^^^^^ + +.. versionadded:: 2.2 + +Default: ``False`` + +This is an Oracle-specific setting. + +If set to ``True``, Oracle Managed Files (OMF) tablespaces will be used. +:setting:`DATAFILE` and :setting:`DATAFILE_TMP` will be ignored. + .. setting:: TEST_TBLSPACE ``TBLSPACE`` diff --git a/docs/releases/2.2.txt b/docs/releases/2.2.txt index 8a7a75a0bc..debc60c5f6 100644 --- a/docs/releases/2.2.txt +++ b/docs/releases/2.2.txt @@ -257,6 +257,9 @@ Tests serialization of list and tuple ``data`` when ``content_type='application/json'``. +* The new :setting:`ORACLE_MANAGED_FILES ` test + database setting allows using Oracle Managed Files (OMF) tablespaces. + URLs ~~~~ diff --git a/tests/backends/oracle/test_creation.py b/tests/backends/oracle/test_creation.py index 1688c4efd2..f090a0ac89 100644 --- a/tests/backends/oracle/test_creation.py +++ b/tests/backends/oracle/test_creation.py @@ -74,3 +74,22 @@ class DatabaseCreationTests(TestCase): creation._create_test_db(verbosity=0, keepdb=False) with self.assertRaises(SystemExit): creation._create_test_db(verbosity=0, keepdb=True) + + def test_oracle_managed_files(self, *mocked_objects): + def _execute_capture_statements(self, cursor, statements, parameters, verbosity, allow_quiet_fail=False): + self.tblspace_sqls = statements + + creation = DatabaseCreation(connection) + # Simulate test database creation with Oracle Managed File (OMF) + # tablespaces. + with mock.patch.object(DatabaseCreation, '_test_database_oracle_managed_files', return_value=True): + with self.patch_execute_statements(_execute_capture_statements): + with connection.cursor() as cursor: + creation._execute_test_db_creation(cursor, creation._get_test_db_params(), verbosity=0) + tblspace_sql, tblspace_tmp_sql = creation.tblspace_sqls + # Datafile names shouldn't appear. + self.assertIn('DATAFILE SIZE', tblspace_sql) + self.assertIn('TEMPFILE SIZE', tblspace_tmp_sql) + # REUSE cannot be used with OMF. + self.assertNotIn('REUSE', tblspace_sql) + self.assertNotIn('REUSE', tblspace_tmp_sql)