001/*
002 *  Copyright 2021 Anyware Services
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 */
016package org.ametys.cms.search.query;
017
018import java.util.Map;
019
020/**
021 * Represents a {@link Query} testing a geocode field.
022 */
023public class GeocodeQuery extends AbstractFieldQuery
024{
025    
026    /** The operator. */
027    protected Operator _operator;
028    
029    /** The value. */
030    protected Map<String, Integer> _value;
031
032    /**
033     * Build a Geocode testing the existence of the field.
034     * @param fieldPath the field path
035     */
036    public GeocodeQuery(String fieldPath)
037    {
038        this(fieldPath, Operator.EXISTS, null);
039    }
040    
041    /**
042     * Build a Geocode query.
043     * @param fieldPath the field's path
044     * @param operator the operator.
045     * @param value the value.
046     */
047    public GeocodeQuery(String fieldPath, Operator operator, Map<String, Integer> value)
048    {
049        super(fieldPath);
050
051        if (Operator.EQ != operator && Operator.NE != operator && Operator.EXISTS != operator)
052        {
053            throw new IllegalArgumentException("Test operator '" + operator + "' is unknown for test's expression.");
054        }
055        
056        _operator = operator;
057        _value = value;
058    }
059    
060    @Override
061    public String build() throws QuerySyntaxException
062    {
063        StringBuilder query = new StringBuilder();
064        
065        if (_operator == Operator.EXISTS)
066        {
067            query.append(_fieldPath).append("_geo:[-90,-180 TO 90,180]");
068            return query.toString();
069        }
070        
071        if (_operator == Operator.NE)
072        {
073            NotQuery.appendNegation(query);
074        }
075        
076        query.append(_fieldPath).append("_geo:[")
077        .append(_value.get("latitude")).append(",").append(_value.get("longitude"))
078        .append(" TO ")
079        .append(_value.get("latitude")).append(",").append(_value.get("longitude"))
080        .append("]");
081        return query.toString();
082        
083    }
084
085    @Override
086    public int hashCode()
087    {
088        final int prime = 31;
089        int result = super.hashCode();
090        result = prime * result + ((_operator == null) ? 0 : _operator.hashCode());
091        result = prime * result + ((_value == null) ? 0 : _value.hashCode());
092        return result;
093    }
094
095    @Override
096    public boolean equals(Object obj)
097    {
098        if (this == obj)
099        {
100            return true;
101        }
102        if (!super.equals(obj))
103        {
104            return false;
105        }
106        if (getClass() != obj.getClass())
107        {
108            return false;
109        }
110        GeocodeQuery other = (GeocodeQuery) obj;
111        if (_operator != other._operator)
112        {
113            return false;
114        }
115        if (_value == null)
116        {
117            if (other._value != null)
118            {
119                return false;
120            }
121        }
122        else if (!_value.equals(other._value))
123        {
124            return false;
125        }
126        return true;
127    }
128}