PostgreSQLQueryObject.java

  1. /*
  2.  * GovWay - A customizable API Gateway
  3.  * https://govway.org
  4.  *
  5.  * Copyright (c) 2005-2025 Link.it srl (https://link.it).
  6.  *
  7.  * This program is free software: you can redistribute it and/or modify
  8.  * it under the terms of the GNU General Public License version 3, as published by
  9.  * the Free Software Foundation.
  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, see <http://www.gnu.org/licenses/>.
  18.  *
  19.  */



  20. package org.openspcoop2.utils.sql;

  21. import java.text.SimpleDateFormat;
  22. import java.util.Date;
  23. import java.util.Iterator;

  24. import org.openspcoop2.utils.TipiDatabase;
  25. import org.openspcoop2.utils.date.DateUtils;


  26. /**
  27.  * Classe dove vengono forniti utility per la conversione di comandi SQL per il database postgresql
  28.  *
  29.  *
  30.  * @author Poli Andrea (apoli@link.it)
  31.  * @author $Author$
  32.  * @version $Rev$, $Date$
  33.  */
  34. public class PostgreSQLQueryObject extends SQLQueryObjectCore{
  35.    
  36.    
  37.    
  38.     public PostgreSQLQueryObject(TipiDatabase tipoDatabase) {
  39.         super(tipoDatabase);
  40.     }

  41.    
  42.    
  43.    
  44.     /**
  45.      * Ritorna una costante  di tipo 'timestamp'
  46.      *
  47.      * @param date Costante
  48.      */
  49.     @Override
  50.     public String getSelectTimestampConstantField(Date date) throws SQLQueryObjectException{
  51.         SimpleDateFormat sqlDateformat = DateUtils.getDefaultDateTimeFormatter("yyyy-MM-dd HH:mm:ss.SSS");
  52.         return "timestamp '"+sqlDateformat.format(date)+"'";
  53.     }
  54.    
  55.    
  56.    

  57.     @Override
  58.     public String getUnixTimestampConversion(String column){
  59.         return "(date_part('epoch',"+column+")*1000)";
  60.     }
  61.    
  62.     @Override
  63.     public String getDiffUnixTimestamp(String columnMax,String columnMin){
  64.         return getUnixTimestampConversion("( "+columnMax+" - "+columnMin+" )");
  65.     }

  66.    
  67.    
  68.    
  69.    
  70.     /**
  71.      * Aggiunge un field count alla select, con un alias, del campo <var>fieldAvg</var> (di tipo Timestamp)
  72.      * es: SELECT avg(fieldAvg) as alias FROM ....
  73.      *
  74.       * @param field Nome del Field
  75.      * @param alias Alias
  76.      */
  77.     @Override
  78.     public ISQLQueryObject addSelectAvgTimestampField(String field,String alias) throws SQLQueryObjectException{
  79.         if(field==null)
  80.             throw new SQLQueryObjectException(SQLQueryObjectCore.FIELD_DEVE_ESSERE_DIVERSO_NULL);
  81.         // Trasformo in UNIX_TIMESTAMP
  82.         String fieldSQL = "avg("+this.getUnixTimestampConversion(field)+")";
  83.         if(alias != null){
  84.             /**fieldSQL = fieldSQL + " as "+alias;*/
  85.             fieldSQL = fieldSQL + this.getDefaultAliasFieldKeyword()+alias;
  86.         }
  87.         this.engineAddSelectField(null,fieldSQL,null,false,true);
  88.         this.fieldNames.add(alias);
  89.         return this;
  90.     }
  91.    
  92.    
  93.     /**
  94.      * Aggiunge un field count alla select, con un alias, del campo <var>field</var> (di tipo Timestamp)
  95.      * es: SELECT max(field) as alias FROM ....
  96.      *
  97.       * @param field Nome del Field
  98.      * @param alias Alias
  99.      */
  100.     @Override
  101.     public ISQLQueryObject addSelectMaxTimestampField(String field,String alias) throws SQLQueryObjectException{
  102.         if(field==null)
  103.             throw new SQLQueryObjectException(SQLQueryObjectCore.FIELD_DEVE_ESSERE_DIVERSO_NULL);
  104.         // Trasformo in UNIX_TIMESTAMP
  105.         String fieldSQL = "max("+this.getUnixTimestampConversion(field)+")";
  106.         if(alias != null){
  107.             /**fieldSQL = fieldSQL + " as "+alias;*/
  108.             fieldSQL = fieldSQL + this.getDefaultAliasFieldKeyword()+alias;
  109.         }
  110.         this.engineAddSelectField(null,fieldSQL,null,false,true);
  111.         this.fieldNames.add(alias);
  112.         return this;
  113.     }
  114.    
  115.     /**
  116.      * Aggiunge un field count alla select, con un alias, del campo <var>field</var> (di tipo Timestamp)
  117.      * es: SELECT min(field) as alias FROM ....
  118.      *
  119.      * @param field Nome del Field
  120.      * @param alias
  121.      */
  122.     @Override
  123.     public ISQLQueryObject addSelectMinTimestampField(String field,String alias) throws SQLQueryObjectException{
  124.         if(field==null)
  125.             throw new SQLQueryObjectException(SQLQueryObjectCore.FIELD_DEVE_ESSERE_DIVERSO_NULL);
  126.         // Trasformo in UNIX_TIMESTAMP
  127.         String fieldSQL = "min("+this.getUnixTimestampConversion(field)+")";
  128.         if(alias != null){
  129.             /**fieldSQL = fieldSQL + " as "+alias;*/
  130.             fieldSQL = fieldSQL + this.getDefaultAliasFieldKeyword()+alias;
  131.         }
  132.         this.engineAddSelectField(null,fieldSQL,null,false,true);
  133.         this.fieldNames.add(alias);
  134.         return this;
  135.     }
  136.    
  137.    
  138.     /**
  139.      * Aggiunge un field count alla select, con un alias, del campo <var>field</var> (di tipo Timestamp)
  140.      * es: SELECT sum(field) as alias FROM ....
  141.      *
  142.      * @param field Nome del Field
  143.      * @param alias
  144.      */
  145.     @Override
  146.     public ISQLQueryObject addSelectSumTimestampField(String field,String alias) throws SQLQueryObjectException{
  147.         if(field==null)
  148.             throw new SQLQueryObjectException(SQLQueryObjectCore.FIELD_DEVE_ESSERE_DIVERSO_NULL);
  149.         // Trasformo in UNIX_TIMESTAMP
  150.         String fieldSQL = "sum("+this.getUnixTimestampConversion(field)+")";
  151.         if(alias != null){
  152.             /**fieldSQL = fieldSQL + " as "+alias;*/
  153.             fieldSQL = fieldSQL + this.getDefaultAliasFieldKeyword()+alias;
  154.         }
  155.         this.engineAddSelectField(null,fieldSQL,null,false,true);
  156.         this.fieldNames.add(alias);
  157.         return this;
  158.     }
  159.    
  160.    
  161.     /**
  162.      * Aggiunge una tabella di ricerca del from
  163.      * es: SELECT * from ( subSelect )
  164.      *
  165.      * @param subSelect subSelect
  166.      */
  167.     @Override
  168.     public ISQLQueryObject addFromTable(ISQLQueryObject subSelect) throws SQLQueryObjectException{
  169.         StringBuilder bf = new StringBuilder();
  170.         bf.append(" ( ");
  171.         bf.append(subSelect.createSQLQuery());
  172.         bf.append(SQLQueryObjectCore.AS_SUBQUERY_SUFFIX+getSerial()+" ");
  173.         this.addFromTable(bf.toString());
  174.         return this;
  175.     }
  176.    
  177.    
  178.    
  179.    
  180.     @Override
  181.     protected EscapeSQLConfiguration getEscapeSQLConfiguration(){
  182.        
  183.         EscapeSQLConfiguration config = new EscapeSQLConfiguration();
  184.         config.addCharacter('_');
  185.         config.addCharacter('%');
  186.         config.addCharacter('\\');
  187.         config.setUseEscapeClausole(false);
  188.         config.setEscape('\\');
  189.        
  190.         // special
  191.         config.addCharacterWithOtherEscapeChar('\'','\'');
  192.        
  193.         return config;
  194.     }

  195.    
  196.    
  197.    
  198.    
  199.    
  200.     @Override
  201.     public String getExtractDayFormatFromTimestampFieldPrefix(DayFormatEnum dayFormat) throws SQLQueryObjectException {
  202.         if(dayFormat==null) {
  203.             throw new SQLQueryObjectException("dayFormat undefined");
  204.         }
  205.         if(DayFormatEnum.FULL_DAY_NAME.equals(dayFormat)) {
  206.             return "TRIM(BOTH FROM TO_CHAR(";
  207.         }
  208.         else {
  209.             return super.getExtractDayFormatFromTimestampFieldPrefix(dayFormat);
  210.         }
  211.     }
  212.     @Override
  213.     public String getExtractDayFormatFromTimestampFieldSuffix(DayFormatEnum dayFormat) throws SQLQueryObjectException {
  214.         if(DayFormatEnum.FULL_DAY_NAME.equals(dayFormat)) {
  215.             return super.getExtractDayFormatFromTimestampFieldSuffix(dayFormat) + ")"; // chiusura trim
  216.         }
  217.         else {
  218.             return super.getExtractDayFormatFromTimestampFieldSuffix(dayFormat);
  219.         }
  220.     }
  221.    
  222.    
  223.    
  224.    
  225.     /**
  226.      * Crea una SQL Query con i dati dell'oggetto
  227.      *
  228.      * @return SQL Query
  229.      */
  230.     @Override
  231.     public String createSQLQuery() throws SQLQueryObjectException{
  232.         return this.createSQLQuery(false);
  233.     }
  234.     private String createSQLQuery(boolean union) throws SQLQueryObjectException{
  235.        
  236.         this.precheckBuildQuery();
  237.        
  238.         StringBuilder bf = new StringBuilder();
  239.        
  240.         bf.append("SELECT ");
  241.        
  242.         // forzatura di indici
  243.         Iterator<String> itForceIndex = this.forceIndexTableNames.iterator();
  244.         while(itForceIndex.hasNext()){
  245.             bf.append(" "+itForceIndex.next()+" ");
  246.         }
  247.        
  248.         if(this.isSelectDistinct())
  249.             bf.append(" DISTINCT ");
  250.        
  251.         // select field
  252.         if(this.fields.isEmpty()){
  253.             bf.append("*");
  254.         }else{
  255.             Iterator<String> it = this.fields.iterator();
  256.             boolean first = true;
  257.             while(it.hasNext()){
  258.                 if(!first)
  259.                     bf.append(",");
  260.                 else
  261.                     first = false;
  262.                 bf.append(it.next());
  263.             }
  264.         }
  265.        
  266.         bf.append(getSQL(false,false,false,union));
  267.        
  268.         /**if( this.offset>=0 || this.limit>=0)
  269.         //  System.out.println("SQL ["+bf.toString()+"]");*/
  270.        
  271.         return bf.toString();
  272.     }

  273.    
  274.     /**
  275.      * Crea una SQL per una operazione di Delete con i dati dell'oggetto
  276.      *
  277.      * @return SQL per una operazione di Delete
  278.      */
  279.     @Override
  280.     public String createSQLDeleteEngine() throws SQLQueryObjectException{
  281.         StringBuilder bf = new StringBuilder();
  282.                
  283.         bf.append("DELETE ");
  284.        
  285.         bf.append(getSQL(true,false,false,false));
  286.         return bf.toString();
  287.     }
  288.    
  289.     /**
  290.      * @return SQL
  291.      * @throws SQLQueryObjectException
  292.      */
  293.     private String getSQL(boolean delete,boolean update,boolean conditions,boolean union) throws SQLQueryObjectException {
  294.         StringBuilder bf = new StringBuilder();

  295.         if(this.selectForUpdate){
  296.             this.checkSelectForUpdate(update, delete, union);
  297.         }
  298.        
  299.         if(!update && !conditions){
  300.             // From
  301.             bf.append(SQLQueryObjectCore.FROM_SEPARATOR);
  302.            
  303.             // Table dove effettuare la ricerca 'FromTable'
  304.             if(this.tables.isEmpty()){
  305.                 throw new SQLQueryObjectException(SQLQueryObjectCore.TABELLA_RICERCA_FROM_NON_DEFINITA);
  306.             }else{
  307.                 if(delete && this.tables.size()>2)
  308.                     throw new SQLQueryObjectException("Non e' possibile effettuare una delete con piu' di una tabella alla volta");
  309.                 Iterator<String> it = this.tables.iterator();
  310.                 boolean first = true;
  311.                 while(it.hasNext()){
  312.                     if(!first)
  313.                         bf.append(",");
  314.                     else
  315.                         first = false;
  316.                     bf.append(it.next());
  317.                 }
  318.             }
  319.         }
  320.        
  321.         // Condizioni di Where
  322.         if(!this.conditions.isEmpty()){
  323.            
  324.             if(!conditions)
  325.                 bf.append(SQLQueryObjectCore.WHERE_SEPARATOR);
  326.            
  327.             if(this.notBeforeConditions){
  328.                 bf.append("NOT (");
  329.             }
  330.            
  331.             for(int i=0; i<this.conditions.size(); i++){
  332.                 if(i>0){
  333.                     if(this.andLogicOperator){
  334.                         bf.append(SQLQueryObjectCore.AND_SEPARATOR);
  335.                     }else{
  336.                         bf.append(SQLQueryObjectCore.OR_SEPARATOR);
  337.                     }
  338.                 }
  339.                 bf.append(this.conditions.get(i));
  340.             }
  341.            
  342.             if(this.notBeforeConditions){
  343.                 bf.append(")");
  344.             }
  345.         }
  346.        
  347.         // Condizione GroupBy
  348.         if((!this.getGroupByConditions().isEmpty()) && (!delete) && (!update) && (!conditions)){
  349.             bf.append(SQLQueryObjectCore.GROUP_BY_SEPARATOR);
  350.             Iterator<String> it = this.getGroupByConditions().iterator();
  351.             boolean first = true;
  352.             while(it.hasNext()){
  353.                 if(!first)
  354.                     bf.append(",");
  355.                 else
  356.                     first = false;
  357.                 bf.append(it.next());
  358.             }
  359.         }
  360.        
  361.         // Condizione OrderBy
  362. /**     if(union==false){ La condizione di OrderBy DEVE essere generata. In SQLServer e MySQL viene generata durante la condizione di LIMIT/OFFSET*/
  363.             if((!this.orderBy.isEmpty()) && (!delete) && (!update) && (!conditions) ){
  364.                 bf.append(SQLQueryObjectCore.ORDER_BY_SEPARATOR);
  365.                 Iterator<String> it = this.orderBy.iterator();
  366.                 boolean first = true;
  367.                 while(it.hasNext()){
  368.                     String column = it.next();
  369.                     if(!first)
  370.                         bf.append(",");
  371.                     else
  372.                         first = false;
  373.                     bf.append(column);
  374.                     boolean sortTypeAsc = this.sortTypeAsc;
  375.                     if(this.orderBySortType.containsKey(column)){
  376.                         sortTypeAsc = this.orderBySortType.get(column);
  377.                     }
  378.                     if(sortTypeAsc){
  379.                         bf.append(SQLQueryObjectCore.ASC_SEPARATOR);
  380.                     }else{
  381.                         bf.append(SQLQueryObjectCore.DESC_SEPARATOR);
  382.                     }
  383.                 }
  384.             }
  385. /**     }*/
  386.        
  387.         // Limit e Offset
  388.         /**if(this.limit>0 || this.offset>0){*/
  389.         // Rilascio vincolo di order by in caso di limit impostato.
  390.         // Il vincolo rimane per l'offset, per gestire le select annidate di qualche implementazioni come Oracle,SQLServer ...
  391.         if(this.offset>=0 &&
  392.             (this.orderBy.isEmpty())
  393.             ){
  394.             throw new SQLQueryObjectException(SQLQueryObjectCore.CONDIZIONI_ORDER_BY_RICHESTE);
  395.         }
  396.        
  397.         // Limit
  398.         if((this.limit>0) && (!delete) && (!update) && (!conditions)){
  399.             bf.append(SQLQueryObjectCore.LIMIT_SEPARATOR);
  400.             bf.append(this.limit);
  401.         }
  402.        
  403.         // Offset
  404.         if((this.offset>=0) && (!delete) && (!update) && (!conditions)){
  405.             bf.append(" OFFSET ");
  406.             bf.append(this.offset);
  407.         }
  408.        
  409.         // ForUpdate
  410.         if(!conditions &&
  411.             (this.selectForUpdate)
  412.             ){
  413.             bf.append(" FOR UPDATE ");
  414.         }
  415.        
  416.         return bf.toString();
  417.     }

  418.    
  419.    
  420.     /**
  421.      * Crea la stringa SQL per l'unione dei parametri presi in sqlQueryObject
  422.      * Il booleano 'unionAll' indica se i vari parametri devono essere uniti con 'UNION'  o con 'UNION ALL'
  423.      *
  424.      * In caso nell'oggetto viene impostato il LIMIT o OFFSET, questo viene utilizzato per effettuare LIMIT e/o OFFSET dell'unione
  425.      *
  426.      * In caso l'ORDER by viene impostato nell'oggetto, questo viene utilizzato per effettuare ORDER BY dell'unione
  427.      *
  428.      *
  429.      * Sintassi PostgreSQL:
  430.      *
  431.      * select * FROM
  432.      * (
  433.      * (  SELECT fields... FROM tabella WHERE conditions  )
  434.      * UNION [ALL]
  435.      * (  SELECT fields... FROM tabella WHERE conditions  )
  436.      * )
  437.      * as subquery
  438.      * ORDER BY gdo,tipo_fruitore,fruitore,tipo_erogatore,erogatore,tipo_servizio,servizio DESC  
  439.      * LIMIT 1000
  440.      * OFFSET 0;
  441.      *
  442.      *
  443.      * @param unionAll
  444.      * @param sqlQueryObject
  445.      * @return stringa SQL per l'unione dei parametri presi in sqlQueryObject
  446.      * @throws SQLQueryObjectException
  447.      */
  448.     @Override
  449.     public String createSQLUnion(boolean unionAll,ISQLQueryObject... sqlQueryObject) throws SQLQueryObjectException{
  450.        
  451.         // Controllo parametro su cui effettuare la UNION
  452.         this.checkUnionField(false,sqlQueryObject);
  453.        
  454.         if(this.selectForUpdate){
  455.             this.checkSelectForUpdate(false, false, true);
  456.         }
  457.        
  458.         StringBuilder bf = new StringBuilder();
  459.        
  460.         bf.append("SELECT ");
  461.        
  462.         // forzatura di indici
  463.         Iterator<String> itForceIndex = this.forceIndexTableNames.iterator();
  464.         while(itForceIndex.hasNext()){
  465.             bf.append(" "+itForceIndex.next()+" ");
  466.         }
  467.        
  468.         // Non ha senso, la union fa gia la distinct, a meno di usare la unionAll ma in quel caso non si vuole la distinct
  469.         /** if(this.isSelectDistinct())
  470.         //  bf.append(" DISTINCT ");*/
  471.        
  472.         // select field
  473.         if(this.fields.isEmpty()){
  474.             bf.append("*");
  475.         }else{
  476.             Iterator<String> it = this.fields.iterator();
  477.             boolean first = true;
  478.             while(it.hasNext()){
  479.                 if(!first)
  480.                     bf.append(",");
  481.                 else
  482.                     first = false;
  483.                 bf.append(it.next());
  484.             }
  485.         }
  486.        
  487.         bf.append(SQLQueryObjectCore.FROM_SEPARATOR_APERTURA);
  488.        
  489.         for(int i=0; i<sqlQueryObject.length; i++){
  490.            
  491.             if(((PostgreSQLQueryObject)sqlQueryObject[i]).selectForUpdate){
  492.                 try{
  493.                     ((PostgreSQLQueryObject)sqlQueryObject[i]).checkSelectForUpdate(false, false, true);
  494.                 }catch(Exception e){
  495.                     throw new SQLQueryObjectException("Parametro SqlQueryObject["+i+"] non valido: "+e.getMessage());
  496.                 }
  497.             }
  498.            
  499.             if(i>0){
  500.                 bf.append(" UNION ");
  501.                 if(unionAll){
  502.                     bf.append(" ALL ");
  503.                 }
  504.             }
  505.            
  506.             bf.append("( ");
  507.            
  508.             bf.append(((PostgreSQLQueryObject)sqlQueryObject[i]).createSQLQuery(true));
  509.            
  510.             bf.append(") ");
  511.         }
  512.        
  513.         bf.append(SQLQueryObjectCore.AS_SUBQUERY_SUFFIX+getSerial()+" ");
  514.        
  515.         // Condizione GroupBy
  516.         if((!this.getGroupByConditions().isEmpty())){
  517.             bf.append(SQLQueryObjectCore.GROUP_BY_SEPARATOR);
  518.             Iterator<String> it = this.getGroupByConditions().iterator();
  519.             boolean first = true;
  520.             while(it.hasNext()){
  521.                 if(!first)
  522.                     bf.append(",");
  523.                 else
  524.                     first = false;
  525.                 bf.append(it.next());
  526.             }
  527.         }
  528.        
  529.         // Condizione OrderBy
  530.         if(!this.orderBy.isEmpty()){
  531.             bf.append(SQLQueryObjectCore.ORDER_BY_SEPARATOR);
  532.             Iterator<String> it = this.orderBy.iterator();
  533.             boolean first = true;
  534.             while(it.hasNext()){
  535.                 String column = it.next();
  536.                 if(!first)
  537.                     bf.append(",");
  538.                 else
  539.                     first = false;
  540.                 bf.append(column);
  541.                 boolean sortTypeAsc = this.sortTypeAsc;
  542.                 if(this.orderBySortType.containsKey(column)){
  543.                     sortTypeAsc = this.orderBySortType.get(column);
  544.                 }
  545.                 if(sortTypeAsc){
  546.                     bf.append(SQLQueryObjectCore.ASC_SEPARATOR);
  547.                 }else{
  548.                     bf.append(SQLQueryObjectCore.DESC_SEPARATOR);
  549.                 }
  550.             }
  551.         }
  552.        
  553.         // Limit e Offset
  554.         /**if(this.limit>0 || this.offset>0){*/
  555.         // Rilascio vincolo di order by in caso di limit impostato.
  556.         // Il vincolo rimane per l'offset, per gestire le select annidate di qualche implementazioni come Oracle,SQLServer ...
  557.         if(this.offset>=0 &&
  558.             (this.orderBy.isEmpty())
  559.             ){
  560.             throw new SQLQueryObjectException(SQLQueryObjectCore.CONDIZIONI_ORDER_BY_RICHESTE);
  561.         }
  562.        
  563.         // Limit
  564.         if(this.limit>0){
  565.             bf.append(SQLQueryObjectCore.LIMIT_SEPARATOR);
  566.             bf.append(this.limit);
  567.         }
  568.        
  569.         // Offset
  570.         if(this.offset>=0){
  571.             bf.append(" OFFSET ");
  572.             bf.append(this.offset);
  573.         }
  574.        
  575.         return bf.toString();
  576.     }
  577.    
  578.     /**
  579.      * Crea la stringa SQL per l'unione dei parametri presi in sqlQueryObject (viene effettuato il count)
  580.      * Il booleano 'unionAll' indica se i vari parametri devono essere uniti con 'UNION'  o con 'UNION ALL'
  581.      *
  582.      * Sintassi PostgreSQL:
  583.      *
  584.      * select count(*) as aliasCount FROM (
  585.      *
  586.      * (  SELECT fields... FROM tabella WHERE conditions  )
  587.      * UNION [ALL]
  588.      * (  SELECT fields... FROM tabella WHERE conditions  )
  589.      *
  590.      * ) as subquery
  591.      *
  592.      * @param unionAll
  593.      * @param sqlQueryObject
  594.      * @return stringa SQL per l'unione dei parametri presi in sqlQueryObject (viene effettuato il count)
  595.      * @throws SQLQueryObjectException
  596.      */
  597.     @Override
  598.     public String createSQLUnionCount(boolean unionAll,String aliasCount,ISQLQueryObject... sqlQueryObject) throws SQLQueryObjectException{
  599.        
  600.         // Controllo parametro su cui effettuare la UNION
  601.         this.checkUnionField(true,sqlQueryObject);
  602.        
  603.         if(aliasCount==null){
  604.             throw new SQLQueryObjectException("Alias per il count non definito");
  605.         }
  606.        
  607.         StringBuilder bf = new StringBuilder();
  608.        
  609.         bf.append("SELECT count(*) "+this.getDefaultAliasFieldKeyword()+" ");
  610.         bf.append(aliasCount);
  611.         bf.append(SQLQueryObjectCore.FROM_SEPARATOR_APERTURA);
  612.                
  613.         bf.append( this.createSQLUnion(unionAll, sqlQueryObject) );
  614.        
  615.         bf.append(SQLQueryObjectCore.AS_SUBQUERY_SUFFIX+getSerial()+" ");
  616.            
  617.         return bf.toString();
  618.        
  619.     }
  620.    
  621.    
  622.     /**
  623.      * Crea una SQL per una operazione di Update con i dati dell'oggetto
  624.      *
  625.      * @return SQL per una operazione di Update
  626.      */
  627.     @Override
  628.     public String createSQLUpdateEngine() throws SQLQueryObjectException{

  629.         StringBuilder bf = new StringBuilder();
  630.         bf.append("UPDATE ");
  631.         bf.append(this.updateTable);
  632.         bf.append(" SET ");
  633.         for(int i=0; i<this.updateFieldsName.size(); i++){
  634.             if(i>0)
  635.                 bf.append(" , ");
  636.             bf.append(this.updateFieldsName.get(i));
  637.             bf.append(" = ");
  638.             bf.append(this.updateFieldsValue.get(i));
  639.         }
  640.         bf.append(getSQL(false,true,false,false));
  641.         return bf.toString();
  642.     }
  643.    
  644.    
  645.    
  646.    
  647.    
  648.    
  649.    
  650.     /* ---------------- WHERE CONDITIONS ------------------ */
  651.    
  652.     /**
  653.      * Crea le condizioni presenti senza anteporre il comando (INSERT,CREATE,UPDATE), le tabelle interessate e il 'WHERE'
  654.      *
  655.      * @return SQL Query
  656.      */
  657.     @Override
  658.     public String createSQLConditionsEngine() throws SQLQueryObjectException{
  659.        
  660.         StringBuilder bf = new StringBuilder();
  661.         bf.append(getSQL(false,false,true,false));
  662.         return bf.toString();
  663.     }
  664. }