plain.models 0.33.1__tar.gz → 0.34.1__tar.gz
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.
- {plain_models-0.33.1 → plain_models-0.34.1}/.gitignore +0 -3
- {plain_models-0.33.1 → plain_models-0.34.1}/PKG-INFO +9 -11
- plain_models-0.34.1/plain/models/CHANGELOG.md +27 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/README.md +8 -10
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/__init__.py +2 -6
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/base.py +10 -18
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/creation.py +3 -4
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/introspection.py +2 -3
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/schema.py +3 -9
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/validation.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/base.py +15 -23
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/schema.py +0 -2
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/base.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/creation.py +2 -2
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/features.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/schema.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/utils.py +2 -6
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backups/core.py +15 -22
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/base.py +179 -225
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/cli.py +25 -62
- plain_models-0.34.1/plain/models/connections.py +77 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/constraints.py +10 -10
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/db.py +7 -15
- plain_models-0.34.1/plain/models/default_settings.py +19 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/deletion.py +14 -16
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/expressions.py +7 -10
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/fields/__init__.py +56 -76
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/fields/json.py +9 -12
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/fields/related.py +5 -17
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/fields/related_descriptors.py +43 -95
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/forms.py +2 -4
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/indexes.py +2 -3
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/lookups.py +0 -7
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/manager.py +1 -14
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/executor.py +0 -16
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/loader.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/migration.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/operations/base.py +4 -11
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/operations/fields.py +4 -4
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/operations/models.py +10 -10
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/operations/special.py +6 -14
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/recorder.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/options.py +4 -7
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/preflight.py +25 -44
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/query.py +47 -102
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/query_utils.py +4 -4
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/sql/compiler.py +7 -11
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/sql/query.py +32 -42
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/sql/subqueries.py +6 -8
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/sql/where.py +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/test/pytest.py +21 -32
- plain_models-0.34.1/plain/models/test/utils.py +11 -0
- plain_models-0.34.1/plain/models/transaction.py +224 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/pyproject.toml +1 -1
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/app/settings.py +3 -5
- plain_models-0.33.1/plain/models/connections.py +0 -194
- plain_models-0.33.1/plain/models/default_settings.py +0 -26
- plain_models-0.33.1/plain/models/test/utils.py +0 -147
- plain_models-0.33.1/plain/models/transaction.py +0 -322
- {plain_models-0.33.1 → plain_models-0.34.1}/LICENSE +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/README.md +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/aggregates.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/client.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/features.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/operations.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/base/validation.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/ddl_references.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/base.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/client.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/compiler.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/creation.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/features.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/introspection.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/operations.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/mysql/schema.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/client.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/creation.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/features.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/introspection.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/postgresql/operations.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/_functions.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/client.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/introspection.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backends/sqlite3/operations.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backups/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backups/cli.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/backups/clients.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/config.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/constants.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/database_url.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/entrypoints.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/enums.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/exceptions.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/fields/mixins.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/fields/related_lookups.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/fields/reverse_related.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/functions/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/functions/comparison.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/functions/datetime.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/functions/math.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/functions/mixins.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/functions/text.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/functions/window.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/autodetector.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/exceptions.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/graph.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/operations/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/optimizer.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/questioner.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/serializer.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/state.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/utils.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/migrations/writer.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/registry.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/sql/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/sql/constants.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/sql/datastructures.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/test/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/plain/models/utils.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/app/examples/migrations/0001_initial.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/app/examples/migrations/0002_test_field_removed.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/app/examples/migrations/__init__.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/app/examples/models.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/app/urls.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/test_database_url.py +0 -0
- {plain_models-0.33.1 → plain_models-0.34.1}/tests/test_models.py +0 -0
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.4
|
2
2
|
Name: plain.models
|
3
|
-
Version: 0.
|
3
|
+
Version: 0.34.1
|
4
4
|
Summary: Database models for Plain.
|
5
5
|
Author-email: Dave Gaeddert <dave.gaeddert@dropseed.dev>
|
6
6
|
License-File: LICENSE
|
@@ -71,19 +71,17 @@ To connect to a database, you can provide a `DATABASE_URL` environment variable.
|
|
71
71
|
DATABASE_URL=postgresql://user:password@localhost:5432/dbname
|
72
72
|
```
|
73
73
|
|
74
|
-
Or you can manually define the `
|
74
|
+
Or you can manually define the `DATABASE` setting.
|
75
75
|
|
76
76
|
```python
|
77
77
|
# app/settings.py
|
78
|
-
|
79
|
-
"
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
"PORT": "5432",
|
86
|
-
}
|
78
|
+
DATABASE = {
|
79
|
+
"ENGINE": "plain.models.backends.postgresql",
|
80
|
+
"NAME": "dbname",
|
81
|
+
"USER": "user",
|
82
|
+
"PASSWORD": "password",
|
83
|
+
"HOST": "localhost",
|
84
|
+
"PORT": "5432",
|
87
85
|
}
|
88
86
|
```
|
89
87
|
|
@@ -0,0 +1,27 @@
|
|
1
|
+
# plain-models changelog
|
2
|
+
|
3
|
+
## [0.34.1](https://github.com/dropseed/plain/releases/plain-models@0.34.1) (2025-06-23)
|
4
|
+
|
5
|
+
### What's changed
|
6
|
+
|
7
|
+
- Fixed Markdown bullet indentation in the 0.34.0 release notes so they render correctly ([2fc81de](https://github.com/dropseed/plain/commit/2fc81de)).
|
8
|
+
|
9
|
+
### Upgrade instructions
|
10
|
+
|
11
|
+
- No changes required
|
12
|
+
|
13
|
+
## [0.34.0](https://github.com/dropseed/plain/releases/plain-models@0.34.0) (2025-06-23)
|
14
|
+
|
15
|
+
### What's changed
|
16
|
+
|
17
|
+
- Switched to a single `DATABASE` setting instead of `DATABASES` and removed `DATABASE_ROUTERS`. A helper still automatically populates `DATABASE` from `DATABASE_URL` just like before ([d346d81](https://github.com/dropseed/plain/commit/d346d81)).
|
18
|
+
- The `plain.models.db` module now exposes a `db_connection` object that lazily represents the active database connection. Previous `connections`, `router`, and `DEFAULT_DB_ALIAS` exports were removed ([d346d81](https://github.com/dropseed/plain/commit/d346d81)).
|
19
|
+
|
20
|
+
### Upgrade instructions
|
21
|
+
|
22
|
+
- Replace any `DATABASES` definition in your settings with a single `DATABASE` dict (keys are identical to the inner dict you were previously using).
|
23
|
+
- Remove any `DATABASE_ROUTERS` configuration – multiple databases are no longer supported.
|
24
|
+
- Update import sites:
|
25
|
+
- `from plain.models import connections` → `from plain.models import db_connection`
|
26
|
+
- `from plain.models import router` → (no longer needed; remove usage or switch to `db_connection` where appropriate)
|
27
|
+
- `from plain.models.connections import DEFAULT_DB_ALIAS` → (constant removed; default database is implicit)
|
@@ -60,19 +60,17 @@ To connect to a database, you can provide a `DATABASE_URL` environment variable.
|
|
60
60
|
DATABASE_URL=postgresql://user:password@localhost:5432/dbname
|
61
61
|
```
|
62
62
|
|
63
|
-
Or you can manually define the `
|
63
|
+
Or you can manually define the `DATABASE` setting.
|
64
64
|
|
65
65
|
```python
|
66
66
|
# app/settings.py
|
67
|
-
|
68
|
-
"
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
"PORT": "5432",
|
75
|
-
}
|
67
|
+
DATABASE = {
|
68
|
+
"ENGINE": "plain.models.backends.postgresql",
|
69
|
+
"NAME": "dbname",
|
70
|
+
"USER": "user",
|
71
|
+
"PASSWORD": "password",
|
72
|
+
"HOST": "localhost",
|
73
|
+
"PORT": "5432",
|
76
74
|
}
|
77
75
|
```
|
78
76
|
|
@@ -8,7 +8,6 @@ from .aggregates import __all__ as aggregates_all
|
|
8
8
|
from .constraints import * # NOQA
|
9
9
|
from .constraints import __all__ as constraints_all
|
10
10
|
from .db import (
|
11
|
-
DEFAULT_DB_ALIAS,
|
12
11
|
PLAIN_VERSION_PICKLE_KEY,
|
13
12
|
DatabaseError,
|
14
13
|
DataError,
|
@@ -20,9 +19,8 @@ from .db import (
|
|
20
19
|
OperationalError,
|
21
20
|
ProgrammingError,
|
22
21
|
close_old_connections,
|
23
|
-
|
22
|
+
db_connection,
|
24
23
|
reset_queries,
|
25
|
-
router,
|
26
24
|
)
|
27
25
|
from .deletion import (
|
28
26
|
CASCADE,
|
@@ -127,8 +125,7 @@ __all__ += [
|
|
127
125
|
|
128
126
|
# DB-related exports
|
129
127
|
__all__ += [
|
130
|
-
"
|
131
|
-
"router",
|
128
|
+
"db_connection",
|
132
129
|
"reset_queries",
|
133
130
|
"close_old_connections",
|
134
131
|
"DatabaseError",
|
@@ -140,7 +137,6 @@ __all__ += [
|
|
140
137
|
"Error",
|
141
138
|
"InterfaceError",
|
142
139
|
"OperationalError",
|
143
|
-
"DEFAULT_DB_ALIAS",
|
144
140
|
"PLAIN_VERSION_PICKLE_KEY",
|
145
141
|
]
|
146
142
|
|
@@ -14,7 +14,6 @@ from plain.models.backends import utils
|
|
14
14
|
from plain.models.backends.base.validation import BaseDatabaseValidation
|
15
15
|
from plain.models.backends.utils import debug_transaction
|
16
16
|
from plain.models.db import (
|
17
|
-
DEFAULT_DB_ALIAS,
|
18
17
|
DatabaseError,
|
19
18
|
DatabaseErrorWrapper,
|
20
19
|
NotSupportedError,
|
@@ -22,8 +21,7 @@ from plain.models.db import (
|
|
22
21
|
from plain.models.transaction import TransactionManagementError
|
23
22
|
from plain.runtime import settings
|
24
23
|
|
25
|
-
|
26
|
-
RAN_DB_VERSION_CHECK = set()
|
24
|
+
RAN_DB_VERSION_CHECK = False
|
27
25
|
|
28
26
|
logger = logging.getLogger("plain.models.backends.base")
|
29
27
|
|
@@ -51,7 +49,7 @@ class BaseDatabaseWrapper:
|
|
51
49
|
|
52
50
|
queries_limit = 9000
|
53
51
|
|
54
|
-
def __init__(self, settings_dict
|
52
|
+
def __init__(self, settings_dict):
|
55
53
|
# Connection related attributes.
|
56
54
|
# The underlying database connection.
|
57
55
|
self.connection = None
|
@@ -59,7 +57,6 @@ class BaseDatabaseWrapper:
|
|
59
57
|
# NAME, USER, etc. It's called `settings_dict` instead of `settings`
|
60
58
|
# to disambiguate it from Plain settings modules.
|
61
59
|
self.settings_dict = settings_dict
|
62
|
-
self.alias = alias
|
63
60
|
# Query logging in debug mode or when explicitly enabled.
|
64
61
|
self.queries_log = deque(maxlen=self.queries_limit)
|
65
62
|
self.force_debug_cursor = False
|
@@ -120,10 +117,7 @@ class BaseDatabaseWrapper:
|
|
120
117
|
self.validation = self.validation_class(self)
|
121
118
|
|
122
119
|
def __repr__(self):
|
123
|
-
return
|
124
|
-
f"<{self.__class__.__qualname__} "
|
125
|
-
f"vendor={self.vendor!r} alias={self.alias!r}>"
|
126
|
-
)
|
120
|
+
return f"<{self.__class__.__qualname__} vendor={self.vendor!r}>"
|
127
121
|
|
128
122
|
def ensure_timezone(self):
|
129
123
|
"""
|
@@ -218,9 +212,9 @@ class BaseDatabaseWrapper:
|
|
218
212
|
def init_connection_state(self):
|
219
213
|
"""Initialize the database connection settings."""
|
220
214
|
global RAN_DB_VERSION_CHECK
|
221
|
-
if
|
215
|
+
if not RAN_DB_VERSION_CHECK:
|
222
216
|
self.check_database_version_supported()
|
223
|
-
RAN_DB_VERSION_CHECK
|
217
|
+
RAN_DB_VERSION_CHECK = True
|
224
218
|
|
225
219
|
def create_cursor(self, name=None):
|
226
220
|
"""Create a cursor. Assume that a connection is established."""
|
@@ -593,8 +587,8 @@ class BaseDatabaseWrapper:
|
|
593
587
|
if not (self.allow_thread_sharing or self._thread_ident == _thread.get_ident()):
|
594
588
|
raise DatabaseError(
|
595
589
|
"DatabaseWrapper objects created in a "
|
596
|
-
"thread can only be used in that same thread. The
|
597
|
-
f"
|
590
|
+
"thread can only be used in that same thread. The connection "
|
591
|
+
f"was created in thread id {self._thread_ident} and this is "
|
598
592
|
f"thread id {_thread.get_ident()}."
|
599
593
|
)
|
600
594
|
|
@@ -656,7 +650,7 @@ class BaseDatabaseWrapper:
|
|
656
650
|
being exposed to potential child threads while (or after) the test
|
657
651
|
database is destroyed. Refs #10868, #17786, #16969.
|
658
652
|
"""
|
659
|
-
conn = self.__class__({**self.settings_dict, "NAME": None}
|
653
|
+
conn = self.__class__({**self.settings_dict, "NAME": None})
|
660
654
|
try:
|
661
655
|
with conn.cursor() as cursor:
|
662
656
|
yield cursor
|
@@ -729,13 +723,11 @@ class BaseDatabaseWrapper:
|
|
729
723
|
finally:
|
730
724
|
self.execute_wrappers.pop()
|
731
725
|
|
732
|
-
def copy(self
|
726
|
+
def copy(self):
|
733
727
|
"""
|
734
728
|
Return a copy of this connection.
|
735
729
|
|
736
730
|
For tests that require two connections to the same database.
|
737
731
|
"""
|
738
732
|
settings_dict = copy.deepcopy(self.settings_dict)
|
739
|
-
|
740
|
-
alias = self.alias
|
741
|
-
return type(self)(settings_dict, alias)
|
733
|
+
return type(self)(settings_dict)
|
@@ -45,7 +45,7 @@ class BaseDatabaseCreation:
|
|
45
45
|
)
|
46
46
|
|
47
47
|
self.connection.close()
|
48
|
-
settings.
|
48
|
+
settings.DATABASE["NAME"] = test_database_name
|
49
49
|
self.connection.settings_dict["NAME"] = test_database_name
|
50
50
|
|
51
51
|
# We report migrate messages at one level lower than that
|
@@ -54,7 +54,6 @@ class BaseDatabaseCreation:
|
|
54
54
|
migrate.callback(
|
55
55
|
package_label=None,
|
56
56
|
migration_name=None,
|
57
|
-
database=self.connection.alias,
|
58
57
|
fake=False,
|
59
58
|
fake_initial=False,
|
60
59
|
plan=False,
|
@@ -219,7 +218,7 @@ class BaseDatabaseCreation:
|
|
219
218
|
|
220
219
|
# Restore the original database name
|
221
220
|
if old_database_name is not None:
|
222
|
-
settings.
|
221
|
+
settings.DATABASE["NAME"] = old_database_name
|
223
222
|
self.connection.settings_dict["NAME"] = old_database_name
|
224
223
|
|
225
224
|
def _destroy_test_db(self, test_database_name, verbosity):
|
@@ -244,7 +243,7 @@ class BaseDatabaseCreation:
|
|
244
243
|
def test_db_signature(self, prefix=""):
|
245
244
|
"""
|
246
245
|
Return a tuple with elements of self.connection.settings_dict (a
|
247
|
-
|
246
|
+
DATABASE setting value) that uniquely identify a database
|
248
247
|
accordingly to the RDBMS particularities.
|
249
248
|
"""
|
250
249
|
settings_dict = self.connection.settings_dict
|
@@ -79,14 +79,13 @@ class BaseDatabaseIntrospection:
|
|
79
79
|
|
80
80
|
def get_migratable_models(self):
|
81
81
|
from plain.models import models_registry
|
82
|
-
from plain.models.db import router
|
83
82
|
from plain.packages import packages_registry
|
84
83
|
|
85
84
|
return (
|
86
85
|
model
|
87
86
|
for package_config in packages_registry.get_package_configs()
|
88
|
-
for model in
|
89
|
-
|
87
|
+
for model in models_registry.get_models(
|
88
|
+
package_label=package_config.package_label
|
90
89
|
)
|
91
90
|
if model._meta.can_migrate(self.connection)
|
92
91
|
)
|
@@ -152,7 +152,7 @@ class BaseDatabaseSchemaEditor:
|
|
152
152
|
def __enter__(self):
|
153
153
|
self.deferred_sql = []
|
154
154
|
if self.atomic_migration:
|
155
|
-
self.atomic = atomic(
|
155
|
+
self.atomic = atomic()
|
156
156
|
self.atomic.__enter__()
|
157
157
|
return self
|
158
158
|
|
@@ -1247,7 +1247,6 @@ class BaseDatabaseSchemaEditor:
|
|
1247
1247
|
fields=None,
|
1248
1248
|
name=None,
|
1249
1249
|
suffix="",
|
1250
|
-
using="",
|
1251
1250
|
col_suffixes=(),
|
1252
1251
|
sql=None,
|
1253
1252
|
opclasses=(),
|
@@ -1262,9 +1261,7 @@ class BaseDatabaseSchemaEditor:
|
|
1262
1261
|
"""
|
1263
1262
|
fields = fields or []
|
1264
1263
|
expressions = expressions or []
|
1265
|
-
compiler = Query(model, alias_cols=False).get_compiler(
|
1266
|
-
connection=self.connection,
|
1267
|
-
)
|
1264
|
+
compiler = Query(model, alias_cols=False).get_compiler()
|
1268
1265
|
columns = [field.column for field in fields]
|
1269
1266
|
sql_create_index = sql or self.sql_create_index
|
1270
1267
|
table = model._meta.db_table
|
@@ -1279,7 +1276,6 @@ class BaseDatabaseSchemaEditor:
|
|
1279
1276
|
sql_create_index,
|
1280
1277
|
table=Table(table, self.quote_name),
|
1281
1278
|
name=IndexName(table, columns, suffix, create_index_name),
|
1282
|
-
using=using,
|
1283
1279
|
columns=(
|
1284
1280
|
self._index_columns(table, columns, col_suffixes, opclasses)
|
1285
1281
|
if columns
|
@@ -1473,9 +1469,7 @@ class BaseDatabaseSchemaEditor:
|
|
1473
1469
|
):
|
1474
1470
|
return None
|
1475
1471
|
|
1476
|
-
compiler = Query(model, alias_cols=False).get_compiler(
|
1477
|
-
connection=self.connection
|
1478
|
-
)
|
1472
|
+
compiler = Query(model, alias_cols=False).get_compiler()
|
1479
1473
|
table = model._meta.db_table
|
1480
1474
|
columns = [field.column for field in fields]
|
1481
1475
|
if name is None:
|
@@ -14,7 +14,7 @@ class DatabaseValidation(BaseDatabaseValidation):
|
|
14
14
|
):
|
15
15
|
return [
|
16
16
|
preflight.Warning(
|
17
|
-
f"{self.connection.display_name} Strict Mode is not set for database connection
|
17
|
+
f"{self.connection.display_name} Strict Mode is not set for the database connection",
|
18
18
|
hint=(
|
19
19
|
f"{self.connection.display_name}'s Strict Mode fixes many data integrity problems in "
|
20
20
|
f"{self.connection.display_name}, such as data truncation upon insertion, by "
|
@@ -15,7 +15,7 @@ from plain.exceptions import ImproperlyConfigured
|
|
15
15
|
from plain.models.backends.base.base import BaseDatabaseWrapper
|
16
16
|
from plain.models.backends.utils import CursorDebugWrapper as BaseCursorDebugWrapper
|
17
17
|
from plain.models.db import DatabaseError as WrappedDatabaseError
|
18
|
-
from plain.models.db import
|
18
|
+
from plain.models.db import db_connection
|
19
19
|
|
20
20
|
# Some of these import psycopg, so import them after checking if it's installed.
|
21
21
|
from .client import DatabaseClient # NOQA isort:skip
|
@@ -185,14 +185,14 @@ class DatabaseWrapper(BaseDatabaseWrapper):
|
|
185
185
|
"service"
|
186
186
|
):
|
187
187
|
raise ImproperlyConfigured(
|
188
|
-
"settings.
|
188
|
+
"settings.DATABASE is improperly configured. "
|
189
189
|
"Please supply the NAME or OPTIONS['service'] value."
|
190
190
|
)
|
191
191
|
if len(settings_dict["NAME"] or "") > self.ops.max_name_length():
|
192
192
|
raise ImproperlyConfigured(
|
193
193
|
"The database name '%s' (%d characters) is longer than " # noqa: UP031
|
194
194
|
"PostgreSQL's limit of %d characters. Supply a shorter NAME "
|
195
|
-
"in settings.
|
195
|
+
"in settings.DATABASE."
|
196
196
|
% (
|
197
197
|
settings_dict["NAME"],
|
198
198
|
len(settings_dict["NAME"]),
|
@@ -374,26 +374,18 @@ class DatabaseWrapper(BaseDatabaseWrapper):
|
|
374
374
|
"and will use the first PostgreSQL database instead.",
|
375
375
|
RuntimeWarning,
|
376
376
|
)
|
377
|
-
|
378
|
-
|
379
|
-
|
380
|
-
|
381
|
-
|
382
|
-
|
383
|
-
|
384
|
-
|
385
|
-
|
386
|
-
|
387
|
-
|
388
|
-
|
389
|
-
try:
|
390
|
-
with conn.cursor() as cursor:
|
391
|
-
yield cursor
|
392
|
-
finally:
|
393
|
-
conn.close()
|
394
|
-
break
|
395
|
-
else:
|
396
|
-
raise
|
377
|
+
conn = self.__class__(
|
378
|
+
{
|
379
|
+
**self.settings_dict,
|
380
|
+
"NAME": db_connection.settings_dict["NAME"],
|
381
|
+
},
|
382
|
+
alias=self.alias,
|
383
|
+
)
|
384
|
+
try:
|
385
|
+
with conn.cursor() as cursor:
|
386
|
+
yield cursor
|
387
|
+
finally:
|
388
|
+
conn.close()
|
397
389
|
|
398
390
|
@cached_property
|
399
391
|
def pg_version(self):
|
@@ -329,7 +329,6 @@ class DatabaseSchemaEditor(BaseDatabaseSchemaEditor):
|
|
329
329
|
fields=None,
|
330
330
|
name=None,
|
331
331
|
suffix="",
|
332
|
-
using="",
|
333
332
|
col_suffixes=(),
|
334
333
|
sql=None,
|
335
334
|
opclasses=(),
|
@@ -348,7 +347,6 @@ class DatabaseSchemaEditor(BaseDatabaseSchemaEditor):
|
|
348
347
|
fields=fields,
|
349
348
|
name=name,
|
350
349
|
suffix=suffix,
|
351
|
-
using=using,
|
352
350
|
col_suffixes=col_suffixes,
|
353
351
|
sql=sql,
|
354
352
|
opclasses=opclasses,
|
@@ -143,7 +143,7 @@ class DatabaseWrapper(BaseDatabaseWrapper):
|
|
143
143
|
settings_dict = self.settings_dict
|
144
144
|
if not settings_dict["NAME"]:
|
145
145
|
raise ImproperlyConfigured(
|
146
|
-
"settings.
|
146
|
+
"settings.DATABASE is improperly configured. "
|
147
147
|
"Please supply the NAME value."
|
148
148
|
)
|
149
149
|
kwargs = {
|
@@ -16,7 +16,7 @@ class DatabaseCreation(BaseDatabaseCreation):
|
|
16
16
|
raw_name = self.connection.settings_dict["TEST"]["NAME"] or ":memory:"
|
17
17
|
# Special in-memory case
|
18
18
|
if raw_name == ":memory:":
|
19
|
-
return
|
19
|
+
return "file:memorydb?mode=memory&cache=shared"
|
20
20
|
|
21
21
|
test_database_name = raw_name
|
22
22
|
|
@@ -68,7 +68,7 @@ class DatabaseCreation(BaseDatabaseCreation):
|
|
68
68
|
test_database_name = self._get_test_db_name(prefix)
|
69
69
|
sig = [self.connection.settings_dict["NAME"]]
|
70
70
|
if self.is_in_memory_db(test_database_name):
|
71
|
-
sig.append(
|
71
|
+
sig.append(":memory:")
|
72
72
|
else:
|
73
73
|
sig.append(test_database_name)
|
74
74
|
return tuple(sig)
|
@@ -40,7 +40,7 @@ class DatabaseFeatures(BaseDatabaseFeatures):
|
|
40
40
|
def supports_json_field(self):
|
41
41
|
with self.connection.cursor() as cursor:
|
42
42
|
try:
|
43
|
-
with transaction.atomic(
|
43
|
+
with transaction.atomic():
|
44
44
|
cursor.execute('SELECT JSON(\'{"a": "b"}\')')
|
45
45
|
except OperationalError:
|
46
46
|
return False
|
@@ -136,7 +136,7 @@ class DatabaseSchemaEditor(BaseDatabaseSchemaEditor):
|
|
136
136
|
"supported on SQLite < 3.26 because it would break referential "
|
137
137
|
"integrity. Try adding `atomic = False` to the Migration class."
|
138
138
|
)
|
139
|
-
with atomic(
|
139
|
+
with atomic():
|
140
140
|
super().alter_field(model, old_field, new_field, strict=strict)
|
141
141
|
# Follow SQLite's documented procedure for performing changes
|
142
142
|
# that don't affect the on-disk content.
|
@@ -129,16 +129,14 @@ class CursorDebugWrapper(CursorWrapper):
|
|
129
129
|
}
|
130
130
|
)
|
131
131
|
logger.debug(
|
132
|
-
"(%.3f) %s; args=%s
|
132
|
+
"(%.3f) %s; args=%s",
|
133
133
|
duration,
|
134
134
|
sql,
|
135
135
|
params,
|
136
|
-
self.db.alias,
|
137
136
|
extra={
|
138
137
|
"duration": duration,
|
139
138
|
"sql": sql,
|
140
139
|
"params": params,
|
141
|
-
"alias": self.db.alias,
|
142
140
|
},
|
143
141
|
)
|
144
142
|
|
@@ -159,15 +157,13 @@ def debug_transaction(connection, sql):
|
|
159
157
|
}
|
160
158
|
)
|
161
159
|
logger.debug(
|
162
|
-
"(%.3f) %s; args=%s
|
160
|
+
"(%.3f) %s; args=%s",
|
163
161
|
duration,
|
164
162
|
sql,
|
165
163
|
None,
|
166
|
-
connection.alias,
|
167
164
|
extra={
|
168
165
|
"duration": duration,
|
169
166
|
"sql": sql,
|
170
|
-
"alias": connection.alias,
|
171
167
|
},
|
172
168
|
)
|
173
169
|
|
@@ -4,7 +4,7 @@ from pathlib import Path
|
|
4
4
|
|
5
5
|
from plain.runtime import PLAIN_TEMP_PATH
|
6
6
|
|
7
|
-
from .. import
|
7
|
+
from .. import db_connection
|
8
8
|
from .clients import PostgresBackupClient, SQLiteBackupClient
|
9
9
|
|
10
10
|
|
@@ -61,19 +61,17 @@ class DatabaseBackup:
|
|
61
61
|
def create(self, **create_kwargs):
|
62
62
|
self.path.mkdir(parents=True, exist_ok=True)
|
63
63
|
|
64
|
-
|
65
|
-
connection = connections[connection_alias]
|
66
|
-
backup_path = self.path / f"{connection_alias}.backup"
|
64
|
+
backup_path = self.path / "default.backup"
|
67
65
|
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
66
|
+
if db_connection.vendor == "postgresql":
|
67
|
+
PostgresBackupClient(db_connection).create_backup(
|
68
|
+
backup_path,
|
69
|
+
pg_dump=create_kwargs.get("pg_dump", "pg_dump"),
|
70
|
+
)
|
71
|
+
elif db_connection.vendor == "sqlite":
|
72
|
+
SQLiteBackupClient(db_connection).create_backup(backup_path)
|
73
|
+
else:
|
74
|
+
raise Exception("Unsupported database vendor")
|
77
75
|
|
78
76
|
return self.path
|
79
77
|
|
@@ -87,18 +85,13 @@ class DatabaseBackup:
|
|
87
85
|
|
88
86
|
def restore(self, **restore_kwargs):
|
89
87
|
for backup_file in self.iter_files():
|
90
|
-
|
91
|
-
|
92
|
-
if not connection:
|
93
|
-
raise Exception(f"Connection {connection_alias} not found")
|
94
|
-
|
95
|
-
if connection.vendor == "postgresql":
|
96
|
-
PostgresBackupClient(connection).restore_backup(
|
88
|
+
if db_connection.vendor == "postgresql":
|
89
|
+
PostgresBackupClient(db_connection).restore_backup(
|
97
90
|
backup_file,
|
98
91
|
pg_restore=restore_kwargs.get("pg_restore", "pg_restore"),
|
99
92
|
)
|
100
|
-
elif
|
101
|
-
SQLiteBackupClient(
|
93
|
+
elif db_connection.vendor == "sqlite":
|
94
|
+
SQLiteBackupClient(db_connection).restore_backup(backup_file)
|
102
95
|
else:
|
103
96
|
raise Exception("Unsupported database vendor")
|
104
97
|
|