I'm using a python workflow that makes frequent SQL calls, with the SQL calls stored in standalone files and formatted using psycopg2 identifiers. I'm trying to modify these calls using dictionary objects, but can't get the SQL calls to format correctly.
An example header of an SQL file would be:
with my_table as (
SELECT DISTINCT ON ("column_A")
left_table."column_b",
left_table."column_c",
{column_identifier}
...
In my Python script I call the following:
col_info = my_dictionary.entry
column_identifier = " ".join([f'left_table."{x}",' for x in col_info])
This looks exactly right, but if I include this in a call
sql_call = py2.sql.SQL(sql).format(
column_identifier=py2.sql.Identifier(column_identifier),
...
)
I receive a formatting error where the parsed columns all look like this:
"left_table.""column_d"", "
If I use Literal instead of Identifier then the SQL call transacts but produces a nonsensical output. I cannot use AsIs because other Identifier calls are used.
The only potential solution I have seen so far is where the entire SQL call is contained within f""" ... """ but since there are multiple, long SQL calls, including them all in the Python script would be very unwieldy. Being able to format these simple lines would be a highly preferable solution.
Thanks
"left_table.""column_d""you did'left_table."{x}",'which double quotedxand thenpy2.sql.Identifier()which double quoted it again. Look at docs here sql, in particular class psycopg2.sql.Identifier ... Multiple strings can be passed to the object to represent a qualified name, i.e. a dot-separated sequence of identifiers. . There are plenty of examples to show how to do this..\"{x}\")column_identifier = " ".join([f'left_table."{x}",' for x in col_info]). Look at the examples in thesqlmodule link above and add the table/column names directly to thesql.SQL().format(). The table/column names will end up double quoted because that is whatsql.Identifier()does. The result if done correctly will be"column_d"not""column_d"".left_tableis part of the call