2

I want to parse out all the columns out of a sql using regular expression, but no idea about parsing sql coming with functions.Like :

 SELECT
   NVL(SUM(MISSIONNO), 0) DISTCNT, COUNT(DISTINCT(USERID)) USERIDCNT
  FROM EVTSUPPLYHIST
 WHERE EVTCODE = #evtCode#
   AND EVTNO = #evtNo#
   AND GIFTCODE = #giftCode#
   AND SUPPLYDT BETWEEN TO_DATE(#startDate#, 'YYYY/MM/DD HH24:MI:SS') 
   AND TO_DATE(#endDate#, 'YYYY/MM/DD HH24:MI:SS')

For this sql above , right results should be DISTCNT and USERIDCNT, as you might guess it's not pure and clean sql, but ibatis-based paremetered sql.Any ideas?

6
  • 1
    I don't think there's a magic bullet, SQL is a language, parsing languages requires writing parsers. I'm sure if you search around, you'll find an SQL parser written in Java. Note that since SQL isn't a regular language, you will not be able to reliably parse it using regular expressions. Commented Feb 27, 2012 at 6:57
  • use sql parser instead of regexp Commented Feb 27, 2012 at 6:58
  • It's not so easy. And you can't do that only with regex because of many nested parentheses. Commented Feb 27, 2012 at 6:59
  • Maybe as a rough first approximation you can look for words preceding a comma or preceding a 'FROM' (after removing new lines from the query) consisting of [a-zA-Z_]? If the query is SELECT COUNT(USERID) FROM USER_INFO what do you want to return? I suppose you could also allow for multiple words in a column name if it was surrounded by back ticks ("SELECT user id FROM ..") Commented Feb 27, 2012 at 7:00
  • I'll do some research on sql parser, but unfortunately ,my sql is not pure and clean sql, that is it's parametered sql in a flavor of ibatis, not sure if it's ok with that, it's worth a research. I've reedited the thread and paste the full sql. thanks Commented Feb 28, 2012 at 2:00

2 Answers 2

3

I'd recommend using one of the many SQL expression parsers, like zql. From their documentation I see, that they create a java objects from an SQL expression and it should be quite trivial to get the column names from that datastructure.

Sign up to request clarification or add additional context in comments.

2 Comments

I tried zql, but seems like it's not well-documented, then I gave up.
They provide some good examples, took me a few minutes to parse a sql query string, but - it will not read your special sql dialect. (unrecognized function NVL) One would have to adapt the JavaCC input files
1

If you can wait after you've executed the query you may get all the informations very easily from the returned ResultSet.

ResultSetMetaData meta = rs.getMetaData();
int colCount = meta.getColumnCount();

for (int i = 0; i < colCount; i++) {
  String colName = meta.getColumnName(i + 1);
}

1 Comment

If it's executed through jdbc, it's totally right. But my scenario is I need get the information without jdbc execution. I'm working on a code generation tool which can generate vo according to the sql.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.