001/*
002 * (C) Copyright 2006-2018 Nuxeo (http://nuxeo.com/) and others.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 *
016 * Contributors:
017 *     Bogdan Stefanescu
018 *     Florent Guillaume
019 */
020package org.nuxeo.ecm.core.query.sql.model;
021
022import org.apache.commons.lang3.StringUtils;
023
024/**
025 * A named reference to a variable (this can be a field or table).
026 * <p>
027 * Can also include a cast.
028 */
029public class Reference implements Operand {
030
031    private static final long serialVersionUID = -1725102431543210430L;
032
033    public final String name;
034
035    public String originalName;
036
037    public final String cast;
038
039    public final EsHint esHint;
040
041    /** Arbitrary info associated to the reference. */
042    public Object info;
043
044    public Reference(String name) {
045        this.name = name;
046        cast = null;
047        esHint = null;
048    }
049
050    /** @since 5.6 */
051    public Reference(String name, String cast) {
052        this.name = name;
053        this.cast = cast;
054        esHint = null;
055    }
056
057    /** @since 9.10 */
058    public Reference(String name, String cast, EsHint hint) {
059        this.name = name;
060        this.cast = cast;
061        this.esHint = hint;
062    }
063
064    /** @since 5.6 */
065    public Reference(Reference other, String cast) {
066        this.name = other.name;
067        this.cast = cast;
068        esHint = null;
069    }
070
071    /** @since 7.3 */
072    public Reference(Reference other, EsHint hint) {
073        this.name = other.name;
074        cast = null;
075        this.esHint = hint;
076    }
077
078    @Override
079    public void accept(IVisitor visitor) {
080        visitor.visitReference(this);
081    }
082
083    public void setInfo(Object info) {
084        this.info = info;
085    }
086
087    public Object getInfo() {
088        return info;
089    }
090
091    @Override
092    public String toString() {
093        if (cast != null) {
094            return cast + '(' + name + ')';
095        } else if (esHint != null) {
096            return esHint.toString() + " " + name;
097        }
098        return name;
099    }
100
101    @Override
102    public boolean equals(Object obj) {
103        if (obj == this) {
104            return true;
105        }
106        if (!(obj instanceof Reference)) {
107            return false;
108        }
109        return equals((Reference) obj);
110    }
111
112    private boolean equals(Reference other) {
113        if (!name.equals(other.name)) {
114            return false;
115        }
116        if (cast != null || other.cast != null) {
117            return StringUtils.equals(cast, other.cast);
118        }
119        if (esHint != null) {
120            return esHint.equals(other.esHint);
121        } else if (other.esHint != null) {
122            return false;
123        }
124        return true;
125    }
126
127    @Override
128    public int hashCode() {
129        int result = 31 + (cast == null ? 0 : cast.hashCode()) + (esHint == null ? 0 : esHint.hashCode());
130        return 31 * result + name.hashCode();
131    }
132
133    public boolean isPathReference() {
134        return false;
135    }
136
137}