Use f-strings in place of .format()

Code transformed like so:

    pip install flynt
    flynt .
    black .
This commit is contained in:
Simon Willison 2020-11-15 15:24:22 -08:00 committed by GitHub
commit 30e64c8d3b
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
35 changed files with 213 additions and 277 deletions

View file

@ -247,7 +247,7 @@ def generate_compound_rows(num):
for a, b, c in itertools.islice(
itertools.product(string.ascii_lowercase, repeat=3), num
):
yield a, b, c, "{}-{}-{}".format(a, b, c)
yield a, b, c, f"{a}-{b}-{c}"
def generate_sortable_rows(num):
@ -258,7 +258,7 @@ def generate_sortable_rows(num):
yield {
"pk1": a,
"pk2": b,
"content": "{}-{}".format(a, b),
"content": f"{a}-{b}",
"sortable": rand.randint(-100, 100),
"sortable_with_nulls": rand.choice([None, rand.random(), rand.random()]),
"sortable_with_nulls_2": rand.choice([None, rand.random(), rand.random()]),
@ -742,7 +742,7 @@ def cli(db_filename, metadata, plugins_path, recreate):
if pathlib.Path(db_filename).exists():
if not recreate:
raise click.ClickException(
"{} already exists, use --recreate to reset it".format(db_filename)
f"{db_filename} already exists, use --recreate to reset it"
)
else:
pathlib.Path(db_filename).unlink()
@ -751,10 +751,10 @@ def cli(db_filename, metadata, plugins_path, recreate):
for sql, params in TABLE_PARAMETERIZED_SQL:
with conn:
conn.execute(sql, params)
print("Test tables written to {}".format(db_filename))
print(f"Test tables written to {db_filename}")
if metadata:
open(metadata, "w").write(json.dumps(METADATA, indent=4))
print("- metadata written to {}".format(metadata))
print(f"- metadata written to {metadata}")
if plugins_path:
path = pathlib.Path(plugins_path)
if not path.exists():
@ -763,7 +763,7 @@ def cli(db_filename, metadata, plugins_path, recreate):
for filepath in test_plugins.glob("*.py"):
newpath = path / filepath.name
newpath.write_text(filepath.open().read())
print(" Wrote plugin: {}".format(newpath))
print(f" Wrote plugin: {newpath}")
if __name__ == "__main__":

View file

@ -130,7 +130,7 @@ def extra_template_vars(
@hookimpl
def prepare_jinja2_environment(env):
env.filters["format_numeric"] = lambda s: "{:,.0f}".format(float(s))
env.filters["format_numeric"] = lambda s: f"{float(s):,.0f}"
@hookimpl
@ -207,7 +207,7 @@ def register_routes():
async def two(request):
name = request.url_vars["name"]
greeting = request.args.get("greeting")
return Response.text("{} {}".format(greeting, name))
return Response.text(f"{greeting} {name}")
async def three(scope, send):
await asgi_send_json(
@ -281,11 +281,7 @@ def startup(datasette):
@hookimpl
def canned_queries(datasette, database, actor):
return {
"from_hook": "select 1, '{}' as actor_id".format(
actor["id"] if actor else "null"
)
}
return {"from_hook": f"select 1, '{actor['id'] if actor else 'null'}' as actor_id"}
@hookimpl
@ -329,9 +325,9 @@ def table_actions(datasette, database, table, actor):
return [
{
"href": datasette.urls.instance(),
"label": "Database: {}".format(database),
"label": f"Database: {database}",
},
{"href": datasette.urls.instance(), "label": "Table: {}".format(table)},
{"href": datasette.urls.instance(), "label": f"Table: {table}"},
]
@ -341,6 +337,6 @@ def database_actions(datasette, database, actor):
return [
{
"href": datasette.urls.instance(),
"label": "Database: {}".format(database),
"label": f"Database: {database}",
}
]

View file

@ -918,7 +918,7 @@ def test_paginate_compound_keys_with_extra_filters(app_client):
],
)
def test_sortable(app_client, query_string, sort_key, human_description_en):
path = "/fixtures/sortable.json?_shape=objects&{}".format(query_string)
path = f"/fixtures/sortable.json?_shape=objects&{query_string}"
fetched = []
page = 0
while path:
@ -969,8 +969,8 @@ def test_sortable_columns_metadata(app_client):
assert "Cannot sort table by content" == response.json["error"]
# no_primary_key has ALL sort options disabled
for column in ("content", "a", "b", "c"):
response = app_client.get("/fixtures/sortable.json?_sort={}".format(column))
assert "Cannot sort table by {}".format(column) == response.json["error"]
response = app_client.get(f"/fixtures/sortable.json?_sort={column}")
assert f"Cannot sort table by {column}" == response.json["error"]
@pytest.mark.parametrize(
@ -1877,7 +1877,7 @@ def test_binary_data_in_json(app_client, path, expected_json, expected_text):
],
)
def test_paginate_using_link_header(app_client, qs):
path = "/fixtures/compound_three_primary_keys.json{}".format(qs)
path = f"/fixtures/compound_three_primary_keys.json{qs}"
num_pages = 0
while path:
response = app_client.get(path)

View file

@ -7,7 +7,7 @@ import time
def test_auth_token(app_client):
"The /-/auth-token endpoint sets the correct cookie"
assert app_client.ds._root_token is not None
path = "/-/auth-token?token={}".format(app_client.ds._root_token)
path = f"/-/auth-token?token={app_client.ds._root_token}"
response = app_client.get(
path,
allow_redirects=False,

View file

@ -82,7 +82,7 @@ def test_insert(canned_write_client):
def test_canned_query_form_csrf_hidden_field(
canned_write_client, query_name, expect_csrf_hidden_field
):
response = canned_write_client.get("/data/{}".format(query_name))
response = canned_write_client.get(f"/data/{query_name}")
html = response.text
fragment = '<input type="hidden" name="csrftoken" value="'
if expect_csrf_hidden_field:
@ -284,10 +284,10 @@ def magic_parameters_client():
def test_magic_parameters(magic_parameters_client, magic_parameter, expected_re):
magic_parameters_client.ds._metadata["databases"]["data"]["queries"]["runme_post"][
"sql"
] = "insert into logs (line) values (:{})".format(magic_parameter)
] = f"insert into logs (line) values (:{magic_parameter})"
magic_parameters_client.ds._metadata["databases"]["data"]["queries"]["runme_get"][
"sql"
] = "select :{} as result".format(magic_parameter)
] = f"select :{magic_parameter} as result"
cookies = {
"ds_actor": magic_parameters_client.actor_cookie({"id": "root"}),
"foo": "bar",
@ -328,7 +328,7 @@ def test_magic_parameters_csrf_json(magic_parameters_client, use_csrf, return_js
if return_json:
qs = "?_json=1"
response = magic_parameters_client.post(
"/data/runme_post{}".format(qs),
f"/data/runme_post{qs}",
{},
csrftoken_from=use_csrf or None,
allow_redirects=False,

View file

@ -162,4 +162,4 @@ def test_uninstall(run_module):
def test_version():
runner = CliRunner()
result = runner.invoke(cli, ["--version"])
assert result.output == "cli, version {}\n".format(__version__)
assert result.output == f"cli, version {__version__}\n"

View file

@ -46,7 +46,7 @@ def test_help_includes(name, filename):
expected = open(str(docs_path / filename)).read()
runner = CliRunner()
result = runner.invoke(cli, name.split() + ["--help"], terminal_width=88)
actual = "$ datasette {} --help\n\n{}".format(name, result.output)
actual = f"$ datasette {name} --help\n\n{result.output}"
# actual has "Usage: cli package [OPTIONS] FILES"
# because it doesn't know that cli will be aliased to datasette
expected = expected.replace("Usage: datasette", "Usage: cli")
@ -67,10 +67,10 @@ def test_plugin_hooks_are_documented(plugin, plugin_hooks_content):
hook_caller = getattr(app.pm.hook, plugin)
arg_names = [a for a in hook_caller.spec.argnames if a != "__multicall__"]
# Check for plugin_name(arg1, arg2, arg3)
expected = "{}({})".format(plugin, ", ".join(arg_names))
expected = f"{plugin}({', '.join(arg_names)})"
assert (
expected in plugin_hooks_content
), "Missing from plugin hook documentation: {}".format(expected)
), f"Missing from plugin hook documentation: {expected}"
@pytest.fixture(scope="session")

View file

@ -62,6 +62,4 @@ def test_build_where(args, expected_where, expected_params):
f = Filters(sorted(args))
sql_bits, actual_params = f.build_where_clauses("table")
assert expected_where == sql_bits
assert {
"p{}".format(i): param for i, param in enumerate(expected_params)
} == actual_params
assert {f"p{i}": param for i, param in enumerate(expected_params)} == actual_params

View file

@ -592,9 +592,7 @@ def test_css_classes_on_body(app_client, path, expected_classes):
def test_templates_considered(app_client, path, expected_considered):
response = app_client.get(path)
assert response.status == 200
assert (
"<!-- Templates considered: {} -->".format(expected_considered) in response.text
)
assert f"<!-- Templates considered: {expected_considered} -->" in response.text
def test_table_html_simple_primary_key(app_client):
@ -607,9 +605,7 @@ def test_table_html_simple_primary_key(app_client):
for expected_col, th in zip(("content",), ths[1:]):
a = th.find("a")
assert expected_col == a.string
assert a["href"].endswith(
"/simple_primary_key?_size=3&_sort={}".format(expected_col)
)
assert a["href"].endswith(f"/simple_primary_key?_size=3&_sort={expected_col}")
assert ["nofollow"] == a["rel"]
assert [
[
@ -730,11 +726,11 @@ def test_table_html_no_primary_key(app_client):
'<td class="col-Link type-pk"><a href="/fixtures/no_primary_key/{}">{}</a></td>'.format(
i, i
),
'<td class="col-rowid type-int">{}</td>'.format(i),
'<td class="col-content type-str">{}</td>'.format(i),
'<td class="col-a type-str">a{}</td>'.format(i),
'<td class="col-b type-str">b{}</td>'.format(i),
'<td class="col-c type-str">c{}</td>'.format(i),
f'<td class="col-rowid type-int">{i}</td>',
f'<td class="col-content type-str">{i}</td>',
f'<td class="col-a type-str">a{i}</td>',
f'<td class="col-b type-str">b{i}</td>',
f'<td class="col-c type-str">c{i}</td>',
]
for i in range(1, 51)
]
@ -782,8 +778,8 @@ def test_table_html_compound_primary_key(app_client):
for expected_col, th in zip(("pk1", "pk2", "content"), ths[1:]):
a = th.find("a")
assert expected_col == a.string
assert th["class"] == ["col-{}".format(expected_col)]
assert a["href"].endswith("/compound_primary_key?_sort={}".format(expected_col))
assert th["class"] == [f"col-{expected_col}"]
assert a["href"].endswith(f"/compound_primary_key?_sort={expected_col}")
expected = [
[
'<td class="col-Link type-pk"><a href="/fixtures/compound_primary_key/a,b">a,b</a></td>',
@ -1100,9 +1096,7 @@ def test_404(app_client, path):
response = app_client.get(path)
assert 404 == response.status
assert (
'<link rel="stylesheet" href="/-/static/app.css?{}'.format(
app_client.ds.app_css_hash()
)
f'<link rel="stylesheet" href="/-/static/app.css?{app_client.ds.app_css_hash()}'
in response.text
)
@ -1293,9 +1287,10 @@ def test_blob_download(app_client, path, expected_filename):
assert response.status == 200
assert response.body == b"\x15\x1c\x02\xc7\xad\x05\xfe"
assert response.headers["x-content-type-options"] == "nosniff"
assert response.headers[
"content-disposition"
] == 'attachment; filename="{}"'.format(expected_filename)
assert (
response.headers["content-disposition"]
== f'attachment; filename="{expected_filename}"'
)
assert response.headers["content-type"] == "application/binary"
@ -1502,9 +1497,7 @@ def test_base_url_affects_metadata_extra_css_urls(app_client_base_url_prefix):
)
def test_edit_sql_link_on_canned_queries(app_client, path, expected):
response = app_client.get(path)
expected_link = '<a href="{}" class="canned-query-edit-sql">Edit SQL</a>'.format(
expected
)
expected_link = f'<a href="{expected}" class="canned-query-edit-sql">Edit SQL</a>'
if expected:
assert expected_link in response.text
else:
@ -1555,10 +1548,10 @@ def test_navigation_menu_links(
for link in should_have_links:
assert (
details.find("a", {"href": link}) is not None
), "{} expected but missing from nav menu".format(link)
), f"{link} expected but missing from nav menu"
if should_not_have_links:
for link in should_not_have_links:
assert (
details.find("a", {"href": link}) is None
), "{} found but should not have been in nav menu".format(link)
), f"{link} found but should not have been in nav menu"

View file

@ -157,7 +157,7 @@ def test_database_hashed(app_client_with_hash, base_url):
ds._config["base_url"] = base_url
db_hash = ds.get_database("fixtures").hash
assert len(db_hash) == 64
expected = "{}fixtures-{}".format(base_url, db_hash[:7])
expected = f"{base_url}fixtures-{db_hash[:7]}"
assert ds.urls.database("fixtures") == expected
assert ds.urls.table("fixtures", "name") == expected + "/name"
assert ds.urls.query("fixtures", "name") == expected + "/name"

View file

@ -11,7 +11,7 @@ import pytest
],
)
def test_add_message_sets_cookie(app_client, qs, expected):
response = app_client.get("/fixtures.message?{}".format(qs))
response = app_client.get(f"/fixtures.message?{qs}")
signed = response.cookies["ds_messages"]
decoded = app_client.ds.unsign(signed, "messages")
assert expected == decoded

View file

@ -34,7 +34,7 @@ def test_plugin_hooks_have_tests(plugin_hook):
for test in tests_in_this_module:
if plugin_hook in test:
ok = True
assert ok, "Plugin hook is missing tests: {}".format(plugin_hook)
assert ok, f"Plugin hook is missing tests: {plugin_hook}"
def test_hook_plugins_dir_plugin_prepare_connection(app_client):
@ -398,7 +398,7 @@ def view_names_client(tmp_path_factory):
def test_view_names(view_names_client, path, view_name):
response = view_names_client.get(path)
assert response.status == 200
assert "view_name:{}".format(view_name) == response.text
assert f"view_name:{view_name}" == response.text
def test_hook_register_output_renderer_no_parameters(app_client):
@ -659,7 +659,7 @@ def test_hook_register_routes_csrftoken(restore_working_directory, tmpdir_factor
with make_app_client(template_dir=templates) as client:
response = client.get("/csrftoken-form/")
expected_token = client.ds._last_request.scope["csrftoken"]()
assert "CSRFTOKEN: {}".format(expected_token) == response.text
assert f"CSRFTOKEN: {expected_token}" == response.text
def test_hook_register_routes_asgi(app_client):
@ -793,14 +793,14 @@ def test_hook_table_actions(app_client, table_or_view):
return []
return [{"label": a.text, "href": a["href"]} for a in details.select("a")]
response = app_client.get("/fixtures/{}".format(table_or_view))
response = app_client.get(f"/fixtures/{table_or_view}")
assert get_table_actions_links(response.text) == []
response_2 = app_client.get("/fixtures/{}?_bot=1".format(table_or_view))
response_2 = app_client.get(f"/fixtures/{table_or_view}?_bot=1")
assert get_table_actions_links(response_2.text) == [
{"label": "From async", "href": "/"},
{"label": "Database: fixtures", "href": "/"},
{"label": "Table: {}".format(table_or_view), "href": "/"},
{"label": f"Table: {table_or_view}", "href": "/"},
]

View file

@ -62,7 +62,7 @@ Service name: input-service
tag = "gcr.io/myproject/datasette"
mock_call.assert_has_calls(
[
mock.call("gcloud builds submit --tag {}".format(tag), shell=True),
mock.call(f"gcloud builds submit --tag {tag}", shell=True),
mock.call(
"gcloud run deploy --allow-unauthenticated --platform=managed --image {} input-service".format(
tag
@ -86,10 +86,10 @@ def test_publish_cloudrun(mock_call, mock_output, mock_which):
cli.cli, ["publish", "cloudrun", "test.db", "--service", "test"]
)
assert 0 == result.exit_code
tag = "gcr.io/{}/datasette".format(mock_output.return_value)
tag = f"gcr.io/{mock_output.return_value}/datasette"
mock_call.assert_has_calls(
[
mock.call("gcloud builds submit --tag {}".format(tag), shell=True),
mock.call(f"gcloud builds submit --tag {tag}", shell=True),
mock.call(
"gcloud run deploy --allow-unauthenticated --platform=managed --image {} test".format(
tag
@ -129,10 +129,10 @@ def test_publish_cloudrun_memory(
assert 2 == result.exit_code
return
assert 0 == result.exit_code
tag = "gcr.io/{}/datasette".format(mock_output.return_value)
tag = f"gcr.io/{mock_output.return_value}/datasette"
mock_call.assert_has_calls(
[
mock.call("gcloud builds submit --tag {}".format(tag), shell=True),
mock.call(f"gcloud builds submit --tag {tag}", shell=True),
mock.call(
"gcloud run deploy --allow-unauthenticated --platform=managed --image {} test --memory {}".format(
tag, memory

View file

@ -457,7 +457,7 @@ def test_check_connection_passes():
def test_call_with_supported_arguments():
def foo(a, b):
return "{}+{}".format(a, b)
return f"{a}+{b}"
assert "1+2" == utils.call_with_supported_arguments(foo, a=1, b=2)
assert "1+2" == utils.call_with_supported_arguments(foo, a=1, b=2, c=3)