Statistics
| Revision:

svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.compat.cdc / org.gvsig.fmap.dal / org.gvsig.fmap.dal.db / org.gvsig.fmap.dal.db.jdbc / src / main / java / org / gvsig / fmap / dal / store / jdbc2 / spi / operations / CountOperation.java @ 46505

History | View | Annotate | Download (7.81 KB)

1
/**
2
 * gvSIG. Desktop Geographic Information System.
3
 *
4
 * Copyright (C) 2007-2020 gvSIG Association.
5
 *
6
 * This program is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU General Public License
8
 * as published by the Free Software Foundation; either version 3
9
 * of the License, or (at your option) any later version.
10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
 * MA  02110-1301, USA.
20
 *
21
 * For any additional information, do not hesitate to contact us
22
 * at info AT gvsig.com, or visit our website www.gvsig.com.
23
 */
24
package org.gvsig.fmap.dal.store.jdbc2.spi.operations;
25

    
26
import java.sql.ResultSet;
27
import java.sql.SQLException;
28
import java.sql.Statement;
29
import java.util.ArrayList;
30
import java.util.List;
31
import org.apache.commons.lang3.StringUtils;
32
import org.gvsig.expressionevaluator.ExpressionBuilder;
33
import org.gvsig.fmap.dal.SQLBuilder.SelectBuilder;
34
import org.gvsig.fmap.dal.exception.DataException;
35
import org.gvsig.fmap.dal.feature.FeatureQuery;
36
import org.gvsig.fmap.dal.feature.FeatureType;
37
import org.gvsig.fmap.dal.store.jdbc.exception.JDBCSQLException;
38
import org.gvsig.fmap.dal.store.jdbc2.JDBCConnection;
39
import org.gvsig.fmap.dal.store.jdbc2.JDBCHelper;
40
import org.gvsig.fmap.dal.store.jdbc2.JDBCUtils;
41
import org.gvsig.fmap.dal.store.jdbc2.OperationsFactory.TableReference;
42
import org.gvsig.fmap.dal.store.jdbc2.spi.JDBCSQLBuilderBase;
43
import static org.gvsig.fmap.dal.store.jdbc2.spi.JDBCSQLBuilderBase.PROP_FEATURE_TYPE;
44
import static org.gvsig.fmap.dal.store.jdbc2.spi.JDBCSQLBuilderBase.PROP_JDBCHELPER;
45
import static org.gvsig.fmap.dal.store.jdbc2.spi.JDBCSQLBuilderBase.PROP_QUERY;
46
import static org.gvsig.fmap.dal.store.jdbc2.spi.JDBCSQLBuilderBase.PROP_SYMBOLTABLE;
47
import static org.gvsig.fmap.dal.store.jdbc2.spi.JDBCSQLBuilderBase.PROP_TABLE;
48
import static org.gvsig.fmap.dal.store.jdbc2.spi.operations.ResultSetForSetProviderOperation.getAllExtraColumns;
49
import static org.gvsig.fmap.dal.store.jdbc2.spi.operations.ResultSetForSetProviderOperation.process2_ComputedFields;
50
import static org.gvsig.fmap.dal.store.jdbc2.spi.operations.ResultSetForSetProviderOperation.process3_Where;
51
import static org.gvsig.fmap.dal.store.jdbc2.spi.operations.ResultSetForSetProviderOperation.process4_Aggregates;
52
import static org.gvsig.fmap.dal.store.jdbc2.spi.operations.ResultSetForSetProviderOperation.process5_GroupBys;
53

    
54
public class CountOperation extends AbstractConnectionOperation {
55

    
56
    private final TableReference table;
57
    private final String baseFilter;
58
    private final FeatureQuery query;
59
    private final FeatureType featureType;
60

    
61
    public CountOperation(
62
            JDBCHelper helper
63
        ) {
64
        this(helper, null, null, null, null);
65
    }
66

    
67
    public CountOperation(
68
            JDBCHelper helper,
69
            FeatureType featureType,
70
            TableReference table,
71
            String baseFilter,
72
            FeatureQuery query
73
        ) {
74
        super(helper);
75
        this.featureType = featureType;
76
        this.table = table;
77
        this.baseFilter = baseFilter;
78
        this.query = query;
79
    }
80

    
81
    @Override
82
    public final Object perform(JDBCConnection conn) throws DataException {
83
        return this.count(conn);
84
    }
85

    
86
    public String getSQL() {
87
        JDBCSQLBuilderBase sqlbuilder = this.createSQLBuilder();
88
        ExpressionBuilder expbuilder = sqlbuilder.expression();
89

    
90
        SelectBuilder select = sqlbuilder.select();
91
        select.from().table()
92
                .database(this.table.getDatabase())
93
                .schema(this.table.getSchema())
94
                .name(this.table.getTable());
95
        select.from().subquery(this.table.getSubquery());
96

    
97
        List<ExpressionBuilder.Value> valuesToRemoveFeatureType = new ArrayList<>();
98
        List<String> extraColumnNames = new ArrayList<>();
99

    
100
        if (this.query != null && (query.hasAggregateFunctions() || query.hasGroupByColumns())) {
101
            JDBCSQLBuilderBase subsqlbuilder = this.createSQLBuilder();
102
            SelectBuilder subselect = subsqlbuilder.select();
103
            subselect.from().table()
104
                    .database(this.table.getDatabase())
105
                    .schema(this.table.getSchema())
106
                    .name(this.table.getTable());
107
            subselect.from().subquery(this.table.getSubquery());
108

    
109
            // ?sobra?
110
            process2_ComputedFields(helper, featureType, query, sqlbuilder, subselect, extraColumnNames);
111
            
112
            process3_Where(helper, featureType, query, sqlbuilder, subselect);
113
            process4_Aggregates(this.table, this.featureType, this.query, getAllExtraColumns(this.featureType, this.query), sqlbuilder, subselect, extraColumnNames);
114
            process5_GroupBys(this.table, this.featureType, this.query, getAllExtraColumns(this.featureType, this.query), sqlbuilder, subselect, extraColumnNames);
115
            
116
            if (!StringUtils.isEmpty(baseFilter)) {
117
                subselect.where().and(expbuilder.toValue(baseFilter));
118
            }
119
            
120
            subsqlbuilder.setProperties(
121
                    ExpressionBuilder.Variable.class,
122
                    PROP_FEATURE_TYPE, this.featureType,
123
                    PROP_TABLE, table,
124
                    PROP_SYMBOLTABLE, this.query == null ? null : this.query.getSymbolTable(),
125
                    PROP_JDBCHELPER, this.helper,
126
                    PROP_QUERY, this.query
127
            );
128
            for (ExpressionBuilder.Value value : valuesToRemoveFeatureType) {
129
                value.setProperty(PROP_FEATURE_TYPE, null);
130
            }
131
            this.helper.expandCalculedColumns(subsqlbuilder);
132
            this.helper.processSpecialFunctions(subsqlbuilder, featureType, extraColumnNames);
133
            String subsql = subselect.toString();
134
            select.from().table()
135
                    .database(this.table.getDatabase())
136
                    .schema(this.table.getSchema())
137
                    .name(this.table.getTable());
138
            select.from().subquery(subsql);
139
        } else {
140
            process3_Where(helper, featureType, query, sqlbuilder, select);
141
            if (!StringUtils.isEmpty(baseFilter)) {
142
                sqlbuilder.select().where().set(expbuilder.custom(baseFilter));
143
            }
144
        }
145

    
146

    
147
        select.remove_all_columns();
148
        select.column().value(sqlbuilder.count().all());
149
        sqlbuilder.setProperties(
150
                null,
151
                PROP_FEATURE_TYPE, this.featureType,
152
                PROP_TABLE, table,
153
                PROP_SYMBOLTABLE, this.query==null? null:this.query.getSymbolTable(),
154
                PROP_JDBCHELPER, this.helper,
155
                PROP_QUERY, this.query
156
        );
157
        this.helper.expandCalculedColumns(sqlbuilder);
158
        this.helper.processSpecialFunctions(sqlbuilder, featureType, null);
159

    
160
        select.remove_all_columns();
161
        select.column().value(sqlbuilder.count().all());
162
        
163
        String sql = select.toString();
164
        LOGGER.debug(sql);
165
        return sql;
166
    }
167

    
168
    public long count(JDBCConnection conn) throws DataException {
169

    
170
        String sql = this.getSQL();
171
        Statement st = null;
172
        ResultSet rs = null;
173
        try {
174
            st = conn.createStatement();
175
            rs = JDBCUtils.executeQuery(st, sql);
176
            if (!rs.next()) {
177
                return 0;
178
            }
179
            return rs.getLong(1);
180

    
181
        } catch (SQLException ex) {
182
            throw new JDBCSQLException(ex,sql);
183
        } finally {
184
            JDBCUtils.closeQuietly(st);
185
            JDBCUtils.closeQuietly(rs);
186
        }
187
    }
188
       
189
}