Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SQL Formatter #156

Closed
nedtwigg opened this issue Oct 21, 2017 · 6 comments
Closed

SQL Formatter #156

nedtwigg opened this issue Oct 21, 2017 · 6 comments

Comments

@nedtwigg
Copy link
Member

I'd ilke a SQL formatter (specifically for formatting Flyway db migration scripts). Hibernate has BasicFormatterImpl and DDLFormatterImpl. They don't do a ton, but they're better than nothing.

The General SQL Parser is really neat, but there's no free version we can distribute. Maaaaybe they'd be interested in publishing a "format-only" version along with our lib? Might be a marketing opportunity for them. I'll email them and invite them to this thread.

Regardless, there are different ways that folks might wanna format sql, but there isn't a language-specific plugin to hang onto like there has been scala, kotlin, gradle, etc.

Here's my proposal:

spotless {
    sql {
        target 'somedir' // have to specify target manually
        hibernateBasicFormatter('optionalHibernateVersion')
        hibernateDdlFormatter('optionalHibernateVersion')
...

If General SQL Parser is interested, we could maybe have something like this:

spotless {
    sql {
        target 'somedir' // have to specify target manually
        generalSqlParser('optionalVersion').dialect(POSTGRES).someOtherOption(SOMEOPT)
...
@nedtwigg
Copy link
Member Author

The hibernate parser can't handle multiple SQL statements, e.g.

ALTER TABLE userinfo ALTER COLUMN id drop DEFAULT;
ALTER TABLE userinfo drop constraint userinfo_pkey cascade;

We could try to detect the ; ourselves and pass the statements to the formatter one-at-a-time, but that is impossible with only regexes.

It looks like the best opensource SQL prettifiers that can handle multiple statements are:

Writing to disk and spawning a VM for every call to FormatterStep.format() is very expensive, but it would open up a world of non-JVM formatters, as required by #119. Since it turns out this is harder than I thought, I'm gonna put this on the back burner for now. But at some point I'll submit some code to core to make it easier to write formatters that shell out to non-JVM environments. It would be great if we could support this and #119 even if they're slow, and then we can always port things to faster integrations in the future.

@baptistemesta
Copy link
Contributor

@nedtwigg
Copy link
Member Author

nedtwigg commented Nov 9, 2017

Thanks! Can't tell if it supports multiple SQL statements or not, and it's not published to maven central. We could maybe copy-paste the code and give credit. They also have support for external formatters, so it appears that they don't love their own implementation.

@baptistemesta
Copy link
Contributor

I'm not sure but I use this formatter in dbeaver itself and it work well for me.
Anyway I would be interested in having this feature also. (the more code spotless keep formatted the happier I am :) )
If you need some hands on this I could try to contribute.

@nedtwigg
Copy link
Member Author

A PR would be great! I added the skeleton of SQL support in the PR above, I would start from there. Be sure to read the contrib guide as well.

If you can copy DBeaver's implementation over without any deps, then it can go in lib. If it needs deps, then it can go in lib-extra.

I would double-check that DBeaver can support multiple SQL statements. If it doesn't support multiple SQL statements in one file, would it still work for you? It wouldn't for me, but if it's enough for you I'm all for it :)

@nedtwigg
Copy link
Member Author

nedtwigg commented Dec 2, 2017

Released in 3.7.0 thanks to @baptistemesta.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants