diff --git a/datasette/views/table_create_alter.py b/datasette/views/table_create_alter.py index f7775479..88bdafc4 100644 --- a/datasette/views/table_create_alter.py +++ b/datasette/views/table_create_alter.py @@ -22,7 +22,6 @@ from datasette.resources import DatabaseResource, TableResource from datasette.utils import ( escape_sqlite, get_outbound_foreign_keys, - sqlite3, table_column_details, ) from datasette.utils.asgi import NotFound, Response @@ -602,7 +601,6 @@ AlterTableOperation = Annotated[ class AlterTableRequest(_StrictPydanticModel): operations: list[AlterTableOperation] = Field(min_length=1) - dry_run: bool = False def _pydantic_errors(validation_error): @@ -1143,14 +1141,6 @@ class TableAlterView(BaseView): return _table_schema_from_conn(operation_conn, table_name) - if alter_request.dry_run: - memory_conn = sqlite3.connect(":memory:") - try: - conn.backup(memory_conn) - return before_schema, apply_operations(memory_conn) - finally: - memory_conn.close() - after_schema = apply_operations(conn) return before_schema, after_schema @@ -1162,7 +1152,7 @@ class TableAlterView(BaseView): return _error([str(e)], 400) altered = before_schema != after_schema - if altered and not alter_request.dry_run: + if altered: await self.ds.track_event( AlterTableEvent( request.actor, @@ -1189,10 +1179,7 @@ class TableAlterView(BaseView): "altered": altered, "schema": after_schema, "before_schema": before_schema, - "operations_applied": ( - 0 if alter_request.dry_run else len(alter_request.operations) - ), - "dry_run": alter_request.dry_run, + "operations_applied": len(alter_request.operations), }, status=200, ) diff --git a/docs/json_api.rst b/docs/json_api.rst index 1db46dd2..a42175f7 100644 --- a/docs/json_api.rst +++ b/docs/json_api.rst @@ -2285,8 +2285,6 @@ The request body should include an ``operations`` array. Each operation has the ] } -Set ``"dry_run": true`` to validate the operations and return the schema that would be created without modifying the table. - Supported operations: * ``add_column`` adds a new column. ``args`` accepts ``name``, optional ``type`` of ``text``, ``integer``, ``float`` or ``blob``, optional ``not_null``, optional literal ``default`` and optional ``default_expr``. If ``not_null`` is ``true`` either a non-null ``default`` or ``default_expr`` is required. @@ -2316,8 +2314,7 @@ A successful response returns the new schema and the previous schema: "altered": true, "schema": "CREATE TABLE ...", "before_schema": "CREATE TABLE ...", - "operations_applied": 7, - "dry_run": false + "operations_applied": 7 } Any errors will return ``{"errors": ["... descriptive message ..."], "ok": false}``, and a ``400`` status code for a bad input or a ``403`` status code for an authentication or permission error. diff --git a/tests/test_api_write.py b/tests/test_api_write.py index 1d16ad26..49f38cde 100644 --- a/tests/test_api_write.py +++ b/tests/test_api_write.py @@ -898,34 +898,6 @@ async def test_alter_table_operations(ds_write): assert event.after_schema == data["schema"] -@pytest.mark.asyncio -async def test_alter_table_dry_run(ds_write): - token = write_token(ds_write, permissions=["at"]) - db = ds_write.get_database("data") - response = await ds_write.client.post( - "/data/docs/-/alter", - json={ - "dry_run": True, - "operations": [ - {"op": "add_column", "args": {"name": "slug", "type": "text"}} - ], - }, - headers=_headers(token), - ) - assert response.status_code == 200, response.text - data = response.json() - assert data["ok"] is True - assert data["dry_run"] is True - assert data["altered"] is True - assert data["operations_applied"] == 0 - assert "slug" in data["schema"] - columns = ( - await db.execute("select name from pragma_table_info('docs') order by cid") - ).dicts() - assert [column["name"] for column in columns] == ["id", "title", "score", "age"] - assert last_event(ds_write) is None - - @pytest.mark.asyncio async def test_alter_table_foreign_key_operations(ds_write): token = write_token(ds_write, permissions=["at"]) @@ -1246,6 +1218,15 @@ async def test_alter_table_permission_denied(ds_write): @pytest.mark.parametrize( "body,expected_error", ( + ( + { + "dry_run": True, + "operations": [ + {"op": "add_column", "args": {"name": "slug", "type": "text"}} + ], + }, + "dry_run: Extra inputs are not permitted", + ), ( {"operations": [{"op": "add_column", "args": {"type": "text"}}]}, "operations.0.add_column.args.name: Field required",