0

I've just started to play a little bit around Solr and managed to get it running within a Tomcat servlet container. I would like now to use the repository approach from Spring Data but got stucked when trying to handle lat/lon fields (i.e.: geospatial data). I would like to store some tweet-like data. This is the schema I am currently using (trying to follow the wiki):

<?xml version="1.0" encoding="UTF-8" ?>
<schema name="tweets" version="1.1">

  <types>

    <fieldType name="string" class="solr.StrField"/>

    <fieldType name="text1" class="solr.TextField">
      <analyzer>
        <tokenizer class="solr.StandardTokenizerFactory"/>
        <filter class="solr.LowerCaseFilterFactory"/>
        <filter class="solr.HunspellStemFilterFactory" 
                dictionary="../../dictionaries/es_ANY.dic" 
                affix="../../dictionaries/es_ANY.aff" 
                ignoreCase="true" />
        <filter class="solr.RemoveDuplicatesTokenFilterFactory"/>
      </analyzer>
    </fieldType>

    <fieldType name="text2" class="solr.TextField">
      <analyzer>
        <tokenizer class="solr.StandardTokenizerFactory"/>
        <filter class="solr.LowerCaseFilterFactory"/>
      </analyzer>
    </fieldType>

    <fieldType name="location" class="solr.LatLonType" subFieldSuffix="_coordinate"/>

    <dynamicField name="*_coordinate"  type="tdouble" indexed="true"  stored="false"/>

    <fieldType name="date" class="solr.DateField"/>

    <fieldType name="long" class="solr.TrieLongField" precisionStep="0" positionIncrementGap="0"/>

  </types>

  <fields>
    <field name="id" type="string" indexed="true" stored="true" multiValued="false"/>
    <field name="username" type="string" indexed="true" stored="true" multiValued="false"/>
    <field name="pictureURL" type="string" indexed="false" stored="true" multiValued="false"/>
    <field name="topic" type="string" indexed="true" stored="true" multiValued="false"/>
    <field name="content" type="text1" indexed="true" stored="true"/>
    <field name="hashtags" type="text2" indexed="true" stored="true"/>
    <field name="geo" type="location" indexed="true" stored="true"/>
    <field name="timestamp" type="date" indexed="true" stored="true"/>
    <field name="_version_" type="long" indexed="true" stored="true"/>
  </fields>

  <uniqueKey>id</uniqueKey>
  <defaultSearchField>id</defaultSearchField>

</schema>

This would work fine without the geo field, which I don't know how to map in my POJO (I tried both using double[] like MongoDB and String in geo field without much success):

public class Tweet {

    @Id
    @Field
    private String id;

    @Field
    private String username;

    @Field
    private String pictureURL;

    @Field
    private String topic;

    @Field
    private String content;

    @Field
    private List<String> hashtags;

    @Field
    private String geo;

    @Field
    private Date timestamp;

    /** Getters/setters omitted **/
}

When mapping the geo field as a simple String ([lat],[lng]) the exception thrown is:

org.springframework.data.solr.UncategorizedSolrException: undefined field: "geo_0_coordinate"; nested exception is org.apache.solr.client.solrj.impl.HttpSolrServer$RemoteSolrException: undefined field: "geo_0_coordinate"

I tried having a look at the project tests but did not find any POJO using geo fields.

Any idea on how to proceed?

Thanks!

jarandaf
  • 4,297
  • 6
  • 38
  • 67
  • For mapping `solr.LatLonType` you can use a `String` or `GeoLocation` property. The cause seems not to be within mapping but rather the query itself as the server responds with an error. What's the query you're executing and what's the result when you directly call the server on the web interface? – Christoph Strobl Oct 23 '13 at 05:02
  • Hi @ChristophStrobl, I'm trying to add new documents to my single core instance and it just works fine without the geo field. Any further suggestions? – jarandaf Oct 23 '13 at 07:32
  • as the `geo` field is not `required` it works without it. you can try having a look a the solr log or use `SolrJConverter` instead of `MappingSolrConverter`. For tests and sample usage please have a look at `ITestMappingSolrConverter#convertsGeoLocationCorrectly`. – Christoph Strobl Oct 23 '13 at 08:44

1 Answers1

0

I finally found a solution. First of all, the geo field should be a GeoLocation:

@Field
private GeoLocation geo;

Another change required takes place in the schema.xml file:

<fieldType name="location" class="solr.LatLonType" subFieldSuffix="_coordinate"/>
<fieldType name="double" class="solr.DoubleField"/>
<dynamicField name="*_coordinate"  type="tdouble" indexed="true"  stored="false"/>

<!-- ... -->

<field name="geo" type="location" indexed="true" stored="true"/>
<field name="geo_0_coordinate" type="double" indexed="true" stored="true" />
<field name="geo_1_coordinate" type="double" indexed="true" stored="true" />

It turns out Solr stores the LatLonTypes internally as a pair of doubles which should be also defined in the schema.

Hope this helps someone else!

jarandaf
  • 4,297
  • 6
  • 38
  • 67
  • Hi @jaranda, I'm using Solr 4.4.0 and spring 3.2.4.RELEASE with spring-data-solr 1.0.0.RELEASE. I think you only need geo field to be of type org.springframework.data.solr.core.geo.GeoLocation and no change is required in schema.xml. Solr Data automatically handle the conversion. – Aamir Yaseen Nov 28 '13 at 17:22