package com.chenyang.druid.sql.dialect.mysql.ast.statement;

import com.chenyang.druid.DbType;
import com.chenyang.druid.sql.ast.SQLCommentHint;
import com.chenyang.druid.sql.ast.SQLExpr;
import com.chenyang.druid.sql.ast.SQLLimit;
import com.chenyang.druid.sql.ast.SQLName;
import com.chenyang.druid.sql.ast.statement.SQLUpdateSetItem;
import com.chenyang.druid.sql.ast.statement.SQLUpdateStatement;
import com.chenyang.druid.sql.dialect.mysql.visitor.MySqlASTVisitor;
import com.chenyang.druid.sql.visitor.SQLASTVisitor;
import java.util.ArrayList;
import java.util.List;

public class MySqlUpdateStatement extends SQLUpdateStatement implements MySqlStatement {
   private SQLLimit limit;
   private boolean lowPriority = false;
   private boolean ignore = false;
   private boolean commitOnSuccess = false;
   private boolean rollBackOnFail = false;
   private boolean queryOnPk = false;
   private SQLExpr targetAffectRow;
   private boolean forceAllPartitions = false;
   private SQLName forcePartition;
   protected List<SQLCommentHint> hints;

   public MySqlUpdateStatement() {
      super(DbType.mysql);
   }

   public SQLLimit getLimit() {
      return this.limit;
   }

   public void setLimit(SQLLimit limit) {
      if (limit != null) {
         limit.setParent(this);
      }

      this.limit = limit;
   }

   protected void accept0(SQLASTVisitor visitor) {
      if (visitor instanceof MySqlASTVisitor) {
         this.accept0((MySqlASTVisitor)visitor);
      } else {
         super.accept0(visitor);
      }

   }

   public void accept0(MySqlASTVisitor visitor) {
      if (visitor.visit(this)) {
         if (this.tableSource != null) {
            this.tableSource.accept(visitor);
         }

         if (this.from != null) {
            this.from.accept(visitor);
         }

         if (this.items != null) {
            for(int i = 0; i < this.items.size(); ++i) {
               SQLUpdateSetItem item = (SQLUpdateSetItem)this.items.get(i);
               if (item != null) {
                  item.accept(visitor);
               }
            }
         }

         if (this.where != null) {
            this.where.accept(visitor);
         }

         if (this.orderBy != null) {
            this.orderBy.accept(visitor);
         }

         if (this.limit != null) {
            this.limit.accept(visitor);
         }

         if (this.hints != null) {
            for(int i = 0; i < this.hints.size(); ++i) {
               SQLCommentHint hint = (SQLCommentHint)this.hints.get(i);
               if (hint != null) {
                  hint.accept(visitor);
               }
            }
         }
      }

      visitor.endVisit(this);
   }

   public boolean isLowPriority() {
      return this.lowPriority;
   }

   public void setLowPriority(boolean lowPriority) {
      this.lowPriority = lowPriority;
   }

   public boolean isIgnore() {
      return this.ignore;
   }

   public void setIgnore(boolean ignore) {
      this.ignore = ignore;
   }

   public boolean isCommitOnSuccess() {
      return this.commitOnSuccess;
   }

   public void setCommitOnSuccess(boolean commitOnSuccess) {
      this.commitOnSuccess = commitOnSuccess;
   }

   public boolean isRollBackOnFail() {
      return this.rollBackOnFail;
   }

   public void setRollBackOnFail(boolean rollBackOnFail) {
      this.rollBackOnFail = rollBackOnFail;
   }

   public boolean isQueryOnPk() {
      return this.queryOnPk;
   }

   public void setQueryOnPk(boolean queryOnPk) {
      this.queryOnPk = queryOnPk;
   }

   public SQLExpr getTargetAffectRow() {
      return this.targetAffectRow;
   }

   public void setTargetAffectRow(SQLExpr targetAffectRow) {
      if (targetAffectRow != null) {
         targetAffectRow.setParent(this);
      }

      this.targetAffectRow = targetAffectRow;
   }

   public boolean equals(Object o) {
      if (this == o) {
         return true;
      } else if (o != null && this.getClass() == o.getClass()) {
         if (!super.equals(o)) {
            return false;
         } else {
            MySqlUpdateStatement that = (MySqlUpdateStatement)o;
            if (this.lowPriority != that.lowPriority) {
               return false;
            } else if (this.ignore != that.ignore) {
               return false;
            } else if (this.commitOnSuccess != that.commitOnSuccess) {
               return false;
            } else if (this.rollBackOnFail != that.rollBackOnFail) {
               return false;
            } else if (this.queryOnPk != that.queryOnPk) {
               return false;
            } else {
               if (this.hints != null) {
                  if (this.hints.equals(that.hints)) {
                     return false;
                  }
               } else if (that.hints != null) {
                  return false;
               }

               if (this.limit != null) {
                  if (!this.limit.equals(that.limit)) {
                     return false;
                  }
               } else if (that.limit != null) {
                  return false;
               }

               return this.targetAffectRow != null ? this.targetAffectRow.equals(that.targetAffectRow) : that.targetAffectRow == null;
            }
         }
      } else {
         return false;
      }
   }

   public int hashCode() {
      int result = super.hashCode();
      result = 31 * result + (this.limit != null ? this.limit.hashCode() : 0);
      result = 31 * result + (this.lowPriority ? 1 : 0);
      result = 31 * result + (this.ignore ? 1 : 0);
      result = 31 * result + (this.commitOnSuccess ? 1 : 0);
      result = 31 * result + (this.rollBackOnFail ? 1 : 0);
      result = 31 * result + (this.queryOnPk ? 1 : 0);
      result = 31 * result + (this.targetAffectRow != null ? this.targetAffectRow.hashCode() : 0);
      result = 31 * result + (this.hints != null ? this.hints.hashCode() : 0);
      return result;
   }

   public SQLName getForcePartition() {
      return this.forcePartition;
   }

   public void setForcePartition(SQLName x) {
      if (x != null) {
         x.setParent(this);
      }

      this.forcePartition = x;
   }

   public boolean isForceAllPartitions() {
      return this.forceAllPartitions;
   }

   public void setForceAllPartitions(boolean forceAllPartitions) {
      this.forceAllPartitions = forceAllPartitions;
   }

   public int getHintsSize() {
      return this.hints == null ? 0 : this.hints.size();
   }

   public List<SQLCommentHint> getHints() {
      if (this.hints == null) {
         this.hints = new ArrayList(2);
      }

      return this.hints;
   }

   public void setHints(List<SQLCommentHint> hints) {
      this.hints = hints;
   }
}
