001package gudusoft.gsqlparser.stmt.oracle;
002
003import gudusoft.gsqlparser.*;
004import gudusoft.gsqlparser.compiler.TVariable;
005import gudusoft.gsqlparser.nodes.*;
006import gudusoft.gsqlparser.nodes.oracle.TInvokerRightsClause;
007import gudusoft.gsqlparser.nodes.oracle.TParallelEnableClause;
008import gudusoft.gsqlparser.nodes.oracle.TResultCacheClause;
009import gudusoft.gsqlparser.stmt.TCommonStoredProcedureSqlStatement;
010
011
012/**
013 * This class represents 3 types of SQL statement:
014 * <ul>
015 * <li> Create function statement, creates or replaces a standalone function or a call specification.
016 * </li>
017 * <li> Declare a function inside a PL/SQL block or package.
018 * </li>
019 * <li> Define a function inside a PL/SQL block or package.
020 * </li>
021 * </ul>
022 *
023 * @see gudusoft.gsqlparser.stmt.TCommonStoredProcedureSqlStatement#declareStatements
024 * @see gudusoft.gsqlparser.stmt.TCommonStoredProcedureSqlStatement#bodyStatements
025*/
026
027/**
028 * Oracle create function.
029 *
030 */
031public class TPlsqlCreateFunction extends TCommonStoredProcedureSqlStatement {
032
033    private boolean isDeterministic;
034    private TInvokerRightsClause invokerRightsClause;
035    private TParallelEnableClause parallelEnableClause;
036    private TResultCacheClause resultCacheClause;
037    private TObjectName implementionType;
038
039    public TObjectName getImplementionType() {
040        return implementionType;
041    }
042
043    public boolean isDeterministic() {
044        return isDeterministic;
045    }
046
047    public TParallelEnableClause getParallelEnableClause() {
048        return parallelEnableClause;
049    }
050
051    public TResultCacheClause getResultCacheClause() {
052        return resultCacheClause;
053    }
054
055    public TInvokerRightsClause getInvokerRightsClause() {
056
057        return invokerRightsClause;
058    }
059    @Override
060    public TObjectName getStoredProcedureName(){
061        return functionName;
062    }
063
064
065    /**
066     * The name that you give to the function that you are declaring or defining.
067     * @return
068     */
069    public TObjectName getFunctionName() {
070        return functionName;
071    }
072    
073    /**
074     * Indicates what's kind of SQL statement this class represents for, create function, declare a function or define a function.
075     * @return
076     */
077    public int getKind() {
078        return kind;
079    }
080
081    private TObjectName functionName = null;
082
083    public void setKind(int kind) {
084        this.kind = kind;
085    }
086
087    private int kind = TBaseType.kind_create;// what's kind of this function
088
089    private boolean ifNotExists = false;
090
091    /**
092     * Indicates whether this CREATE FUNCTION statement carries an IF NOT EXISTS
093     * clause (supported by the Dameng external-function forms).
094     * @return true if IF NOT EXISTS was specified
095     */
096    public boolean isIfNotExists() {
097        return ifNotExists;
098    }
099
100    public void setIfNotExists(boolean ifNotExists) {
101        this.ifNotExists = ifNotExists;
102    }
103
104    public TPlsqlCreateFunction(EDbVendor dbvendor){
105        super(dbvendor);
106        sqlstatementtype = ESqlStatementType.sstplsql_createfunction ;
107        }
108
109    private TCallSpec callSpec = null;
110
111    /**
112     * call specification
113     * @return
114     */
115    public TCallSpec getCallSpec() {
116        return callSpec;
117    }
118
119    void buildsql() {
120    }
121
122
123
124    void clear() {
125    }
126
127    String getasprettytext() {
128        return "";
129    }
130
131    void iterate(TVisitorAbs pvisitor) {
132    }
133
134 //   private TStatementListSqlNode stmts = null;
135
136     public int doParseStatement(TCustomSqlStatement psql) {
137         if (rootNode == null) return -1;
138         if (isWrapped()) return  0;
139         TCreateFunctionSqlNode createFunctionNode = (TCreateFunctionSqlNode)rootNode;
140
141         //super.doParseStatement(psql);
142         if (super.doParseStatement(psql) != 0) return -1;
143         functionName = createFunctionNode.getFunctionName();
144         this.setParameterDeclarations(createFunctionNode.getParameters());
145         this.returnDataType = createFunctionNode.getReturnDataType(); 
146
147         invokerRightsClause = createFunctionNode.getInvokerRightsClause();
148         isDeterministic = createFunctionNode.isDeterministic();
149         parallelEnableClause = createFunctionNode.getParallelEnableClause();
150         resultCacheClause = createFunctionNode.getResultCacheClause();
151
152         this.implementionType = createFunctionNode.getImplementionType();
153         this.callSpec = createFunctionNode.getCallSpec();
154         this.ifNotExists = createFunctionNode.isIfNotExists();
155         setLabelName(createFunctionNode.getLabelName());
156         setEndlabelName(createFunctionNode.getLabelName());
157
158         // push parameterDeclarations into symbolTable
159         if (this.getParameterDeclarations() != null){
160             for(int i=0;i< this.getParameterDeclarations().size();i++){
161                this.getTopStatement().getSymbolTable().push( new TSymbolTableItem(TObjectName.ttobjParameter,this, this.getParameterDeclarations().getParameterDeclarationItem(i)));
162
163                 TParameterDeclaration parameterDeclaration = this.getParameterDeclarations().getParameterDeclarationItem(i);
164                 if (parameterDeclaration.getParameterName() != null){
165                     this.stmtScope.addSymbol(new TVariable(parameterDeclaration.getParameterName(),parameterDeclaration,functionName));
166                 }
167             }
168         }
169
170         if (createFunctionNode.getDeclareStmts() != null){
171            createFunctionNode.getDeclareStmts().doParse(this, ESqlClause.unknown);
172
173             // push variable declare into symbolTable    , and add to declareStatements
174             for(int i=0;i<createFunctionNode.getDeclareStmts().size();i++){
175                this.getTopStatement().getSymbolTable().push( new TSymbolTableItem(TObjectName.ttobjVariable,this,createFunctionNode.getDeclareStmts().getStatementSqlNode(i).getStmt() ));
176                TCustomSqlStatement declareStmt = createFunctionNode.getDeclareStmts().getStatementSqlNode(i).getStmt();
177                this.getDeclareStatements().add(declareStmt);
178             }
179         }
180
181
182         if (createFunctionNode.getStmts() != null){
183            createFunctionNode.getStmts().doParse(this,ESqlClause.unknown);
184             for(int i= 0; i<createFunctionNode.getStmts().size();i++){
185               this.getBodyStatements().add(createFunctionNode.getStmts().getStatementSqlNode(i).getStmt());
186             }
187         }
188
189         if (createFunctionNode.getExceptionClause() != null){
190             createFunctionNode.getExceptionClause().doParse(this,ESqlClause.unknown);
191             this.setExceptionClause(createFunctionNode.getExceptionClause());
192         }
193         
194//        stmts.doParse(this, ESqlClause.unknown);
195
196         if (createFunctionNode.getDeclareStmts() != null){
197           
198             // pop variable declare from symbolTable
199             for(int i=0;i<createFunctionNode.getDeclareStmts().size();i++){
200                this.getTopStatement().getSymbolTable().pop();
201             }
202
203         }
204
205         // pop parameterDeclarations from symbolTable
206         if (this.getParameterDeclarations() != null){
207             for(int i=0;i< this.getParameterDeclarations().size();i++){
208                this.getTopStatement().getSymbolTable().pop();
209             }
210         }
211
212        return 0;
213    }
214
215    public void init(Object arg1)
216    {
217   //     stmts = (TStatementListSqlNode)arg1;
218    }
219
220    private TTypeName returnDataType = null;
221
222    public void setReturnDataType(TTypeName returnDataType) {
223        this.returnDataType = returnDataType;
224    }
225
226    /**
227     * Datatype of value returned by this function.
228     * @return
229     */
230    public TTypeName getReturnDataType() {
231
232        return returnDataType;
233    }
234
235
236    public void accept(TParseTreeVisitor v){
237        v.preVisit(this);
238        v.postVisit(this);
239    }
240
241    public void acceptChildren(TParseTreeVisitor v){
242        v.preVisit(this);
243
244        if (this.getParameterDeclarations() != null) getParameterDeclarations().acceptChildren(v);
245        if (this.getDeclareStatements().size() > 0) this.getDeclareStatements().acceptChildren(v);
246        if ( this.getBodyStatements().size() > 0) getBodyStatements().acceptChildren(v);
247        if (getExceptionClause() != null) getExceptionClause().acceptChildren(v);
248
249        v.postVisit(this);
250    }
251
252    public void setDeterministic(boolean isDeterministic) {
253        this.isDeterministic = isDeterministic;
254    }
255
256    public void setInvokerRightsClause(TInvokerRightsClause invokerRightsClause) {
257        this.invokerRightsClause = invokerRightsClause;
258    }
259
260    public void setParallelEnableClause(TParallelEnableClause parallelEnableClause) {
261        this.parallelEnableClause = parallelEnableClause;
262    }
263
264    public void setResultCacheClause(TResultCacheClause resultCacheClause) {
265        this.resultCacheClause = resultCacheClause;
266    }
267
268    public void setImplementionType(TObjectName implementionType) {
269        this.implementionType = implementionType;
270    }
271
272    public void setFunctionName(TObjectName functionName) {
273        this.functionName = functionName;
274    }
275
276    public void setCallSpec(TCallSpec callSpec) {
277        this.callSpec = callSpec;
278    }
279}