Skip to content

Instantly share code, notes, and snippets.

@squeaky-pl
Created June 19, 2021 10:38
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save squeaky-pl/3ea456f1b2ca421f37a41c962d521ebc to your computer and use it in GitHub Desktop.
Save squeaky-pl/3ea456f1b2ca421f37a41c962d521ebc to your computer and use it in GitHub Desktop.
Select all except some columns POC
# https://twitter.com/catherinedevlin/status/1406056592332648450
import sqlparse
from sqlparse import tokens
from sqlparse.sql import Identifier
from sqlparse.sql import IdentifierList
from sqlparse.sql import Token
type_pattern = [tokens.Wildcard, tokens.Whitespace, tokens.Keyword, tokens.Whitespace]
comma = Token(tokens.Punctuation, ",")
space = Token(tokens.Whitespace, " ")
def intersperse(lst, items):
if not lst:
return []
result = [None, *items] * (len(lst) - 1)
result[0::3] = lst[:-1]
result.append(lst[-1])
return result
def process_without(tokens):
found = False
for i in range(len(tokens) - 5):
if [t.ttype for t in tokens[i : i + 4]] == type_pattern:
if tokens[i + 2].normalized == "WITHOUT" and isinstance(
tokens[i + 4], (IdentifierList, Identifier)
):
found = i
break
if found is not False:
identifiers = tokens[found + 4]
identifiers = (
identifiers.get_identifiers()
if isinstance(identifiers, IdentifierList)
else [identifiers]
)
without_names = {t.get_name() for t in identifiers}
identifiers = [t for t in all_columns if t.get_name() not in without_names]
identifiers = intersperse(identifiers, [comma, space])
identifier_list = IdentifierList(identifiers)
return [*tokens[:found], identifier_list, *tokens[found + 5 :]]
return tokens
all_columns = [Identifier([Token(tokens.Name, n)]) for n in "a,b,x,y".split(",")]
statement = "SELECT * WITHOUT x, y FROM tbl WHERE a = 4"
parsed_statement = sqlparse.parse(statement)[0]
parsed_statement.tokens = process_without(parsed_statement.tokens)
print(str(parsed_statement))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment