~ubuntu-branches/ubuntu/raring/apgdiff/raring

« back to all changes in this revision

Viewing changes to src/main/java/cz/startnet/utils/pgdiff/parsers/CreateTriggerParser.java

  • Committer: Bazaar Package Importer
  • Author(s): Christoph Berg
  • Date: 2010-10-11 09:08:18 UTC
  • mfrom: (2.1.7 sid)
  • Revision ID: james.westby@ubuntu.com-20101011090818-sdw8yfemrnxo328k
Tags: 2.2.2-1
* New upstream version.
* Using changelog included in zipfile, thanks Miroslav for providing this.
* Update manpage.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/**
 
2
 * Copyright 2006 StartNet s.r.o.
 
3
 *
 
4
 * Distributed under MIT license
 
5
 */
1
6
package cz.startnet.utils.pgdiff.parsers;
2
7
 
3
8
import cz.startnet.utils.pgdiff.schema.PgDatabase;
4
9
import cz.startnet.utils.pgdiff.schema.PgTrigger;
5
10
 
6
 
import java.util.regex.Matcher;
7
 
import java.util.regex.Pattern;
8
 
 
9
11
/**
10
 
 * Parses CREATE TRIGGER commands.
 
12
 * Parses CREATE TRIGGER statements.
11
13
 *
12
14
 * @author fordfrog
13
15
 */
14
16
public class CreateTriggerParser {
15
17
 
16
18
    /**
17
 
     * Pattern for parsing CREATE TRIGGER command.
18
 
     */
19
 
    private static final Pattern PATTERN = Pattern.compile(
20
 
            "^CREATE[\\s]+TRIGGER[\\s]+\"?([^\\s\"]+)\"?[\\s]+(BEFORE|AFTER)[\\s]+"
21
 
            + "(INSERT|UPDATE|DELETE)(?:[\\s]+OR[\\s]+)?(INSERT|UPDATE|DELETE)?"
22
 
            + "(?:[\\s]+OR[\\s]+)?(INSERT|UPDATE|DELETE)?[\\s]+"
23
 
            + "ON[\\s]+\"?([^\\s\"]+)\"?[\\s]+(?:FOR[\\s]+)?(?:EACH[\\s]+)?"
24
 
            + "(ROW|STATEMENT)?[\\s]+EXECUTE[\\s]+PROCEDURE[\\s]+([^;]+);$",
25
 
            Pattern.CASE_INSENSITIVE);
26
 
 
27
 
    /**
28
19
     * Creates a new CreateTableParser object.
29
20
     */
30
21
    private CreateTriggerParser() {
31
 
        super();
32
22
    }
33
23
 
34
24
    /**
35
 
     * Parses CREATE TRIGGER command.
 
25
     * Parses CREATE TRIGGER statement.
36
26
     *
37
27
     * @param database database
38
 
     * @param command CREATE TRIGGER command
39
 
     *
40
 
     * @throws ParserException Thrown if problem occured while parsing the
41
 
     *         command.
42
 
     */
43
 
    public static void parse(final PgDatabase database, final String command) {
44
 
        final Matcher matcher = PATTERN.matcher(command.trim());
45
 
 
46
 
        if (matcher.matches()) {
47
 
            final String triggerName = matcher.group(1);
48
 
            final String when = matcher.group(2);
49
 
            final String[] events = new String[3];
50
 
            events[0] = matcher.group(3);
51
 
            events[1] = matcher.group(4);
52
 
            events[2] = matcher.group(5);
53
 
 
54
 
            final String tableName = matcher.group(6);
55
 
            final String fireOn = matcher.group(7);
56
 
            final String procedure = matcher.group(8);
57
 
 
58
 
            final PgTrigger trigger = new PgTrigger();
59
 
            trigger.setBefore("BEFORE".equalsIgnoreCase(when));
60
 
            trigger.setForEachRow(
61
 
                    (fireOn != null) && "ROW".equalsIgnoreCase(fireOn));
62
 
            trigger.setFunction(procedure.trim());
63
 
            trigger.setName(triggerName.trim());
64
 
            trigger.setOnDelete(isEventPresent(events, "DELETE"));
65
 
            trigger.setOnInsert(isEventPresent(events, "INSERT"));
66
 
            trigger.setOnUpdate(isEventPresent(events, "UPDATE"));
67
 
            trigger.setTableName(tableName.trim());
68
 
 
69
 
            database.getDefaultSchema().getTable(
70
 
                    trigger.getTableName()).addTrigger(trigger);
71
 
        } else {
72
 
            throw new ParserException(
73
 
                    ParserException.CANNOT_PARSE_COMMAND + command);
74
 
        }
75
 
    }
76
 
 
77
 
    /**
78
 
     * Returns true if <code>event</code> is present in
79
 
     * <code>events</code>, otherwise false.
80
 
     *
81
 
     * @param events array of events
82
 
     * @param event event to be searched
83
 
     *
84
 
     * @return true if <code>event</code> is present in <code>events</code>,
85
 
     *         otherwise false
86
 
     */
87
 
    private static boolean isEventPresent(final String[] events,
88
 
            final String event) {
89
 
        boolean present = false;
90
 
 
91
 
        for (String curEvent : events) {
92
 
            if (event.equalsIgnoreCase(curEvent)) {
93
 
                present = true;
94
 
 
95
 
                break;
96
 
            }
97
 
        }
98
 
 
99
 
        return present;
 
28
     * @param statement CREATE TRIGGER statement
 
29
     */
 
30
    public static void parse(final PgDatabase database,
 
31
            final String statement) {
 
32
        final Parser parser = new Parser(statement);
 
33
        parser.expect("CREATE", "TRIGGER");
 
34
 
 
35
        final PgTrigger trigger = new PgTrigger();
 
36
        trigger.setName(ParserUtils.getObjectName(parser.parseIdentifier()));
 
37
 
 
38
        if (parser.expectOptional("BEFORE")) {
 
39
            trigger.setBefore(true);
 
40
        } else if (parser.expectOptional("AFTER")) {
 
41
            trigger.setBefore(false);
 
42
        }
 
43
 
 
44
        boolean first = true;
 
45
 
 
46
        while (true) {
 
47
            if (!first && !parser.expectOptional("OR")) {
 
48
                break;
 
49
            }
 
50
            if (parser.expectOptional("INSERT")) {
 
51
                trigger.setOnInsert(true);
 
52
            } else if (parser.expectOptional("UPDATE")) {
 
53
                trigger.setOnUpdate(true);
 
54
            } else if (parser.expectOptional("DELETE")) {
 
55
                trigger.setOnDelete(true);
 
56
            } else if (parser.expectOptional("TRUNCATE")) {
 
57
                trigger.setOnTruncate(true);
 
58
            } else if (first) {
 
59
                break;
 
60
            } else {
 
61
                parser.throwUnsupportedCommand();
 
62
            }
 
63
 
 
64
            first = false;
 
65
        }
 
66
 
 
67
        parser.expect("ON");
 
68
 
 
69
        trigger.setTableName(
 
70
                ParserUtils.getObjectName(parser.parseIdentifier()));
 
71
 
 
72
        if (parser.expectOptional("FOR")) {
 
73
            parser.expectOptional("EACH");
 
74
 
 
75
            if (parser.expectOptional("ROW")) {
 
76
                trigger.setForEachRow(true);
 
77
            } else if (parser.expectOptional("STATEMENT")) {
 
78
                trigger.setForEachRow(false);
 
79
            } else {
 
80
                parser.throwUnsupportedCommand();
 
81
            }
 
82
        }
 
83
 
 
84
        if (parser.expectOptional("WHEN")) {
 
85
            parser.expect("(");
 
86
            trigger.setWhen(parser.getExpression());
 
87
            parser.expect(")");
 
88
        }
 
89
 
 
90
        parser.expect("EXECUTE", "PROCEDURE");
 
91
        trigger.setFunction(parser.getRest());
 
92
 
 
93
        database.getDefaultSchema().getTable(
 
94
                trigger.getTableName()).addTrigger(trigger);
100
95
    }
101
96
}