Example usage for org.apache.solr.client.solrj.util ClientUtils escapeQueryChars

List of usage examples for org.apache.solr.client.solrj.util ClientUtils escapeQueryChars

Introduction

In this page you can find the example usage for org.apache.solr.client.solrj.util ClientUtils escapeQueryChars.

Prototype


public static String escapeQueryChars(String s) 

Source Link

Document

See: <a href="https://www.google.com/?gws_rd=ssl#q=lucene+query+parser+syntax">Lucene query parser syntax</a> for more information on Escaping Special Characters

Usage

From source file:org.lilyproject.indexer.engine.Indexer.java

License:Apache License

/**
 * Deletes all index entries (for all vtags) for the given record.
 *
 * <p>This method requires you obtained the {@link IndexLocker} for the record.
 *//*from w  w  w .  j a v  a 2s.  co m*/
public void delete(RecordId recordId) throws IOException, SolrServerException, ShardSelectorException {
    verifyLock(recordId);
    solrServers.getSolrServer(recordId)
            .deleteByQuery("@@id:" + ClientUtils.escapeQueryChars(recordId.toString()));
    metrics.deletesByQuery.inc();
}

From source file:org.lilyproject.indexer.engine.test.IndexerTest.java

License:Apache License

@Test
public void testIndexerNonVersioned() throws Exception {
    changeIndexUpdater("indexerconf1.xml");

    messageVerifier.init();/*from   ww  w. j  a  v a2  s  . co m*/

    //
    // Basic create-update-delete
    //
    {
        // Create a record
        log.debug("Begin test NV1");
        Record record = defaultTable.newRecord();
        record.setRecordType(nvRecordType1.getName());
        record.setField(nvfield1.getName(), "nvapple");
        record.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, record.getId(), nvfield1.getId(), nvTag.getId());
        record = defaultTable.create(record);

        commitIndex();
        verifyResultCount("lily.id:" + record.getId().toString(), 1);
        verifyResultCount("nv_field1:nvapple", 1);

        // Update the record
        log.debug("Begin test NV2");
        record.setField(nvfield1.getName(), "nvpear");
        expectEvent(UPDATE, Table.RECORD.name, record.getId(), nvfield1.getId());
        defaultTable.update(record);

        System.out.println("Updated " + record.getId());
        commitIndex();
        verifyResultCount("nv_field1:nvpear", 1);
        verifyResultCount("nv_field1:nvapple", 0);

        // Do as if field2 changed, while field2 is not present in the document.
        // Such situations can occur if the record is modified before earlier events are processed.
        log.debug("Begin test NV3");
        // TODO send event directly to the Indexer
        // sendEvent(EVENT_RECORD_UPDATED, record.getId(), nvfield2.getId());

        verifyResultCount("nv_field1:nvpear", 1);
        verifyResultCount("nv_field1:nvapple", 0);

        // Add a vtag field pointing to a version. For versionless records, this should have no effect
        log.debug("Begin test NV4");
        record.setField(liveTag.getName(), new Long(1));
        expectEvent(UPDATE, Table.RECORD.name, record.getId(), liveTag.getId());
        defaultTable.update(record);

        commitIndex();
        verifyResultCount("nv_field1:nvpear", 1);
        verifyResultCount("nv_field1:nvapple", 0);

        // Delete the record
        log.debug("Begin test NV5");
        expectEvent(DELETE, Table.RECORD.name, record.getId());
        defaultTable.delete(record.getId());

        commitIndex();

        verifyResultCount("nv_field1:nvpear", 0);
    }

    //
    // Deref
    //
    {
        log.debug("Begin test NV6");
        Record record1 = defaultTable.newRecord();
        record1.setRecordType(nvRecordType1.getName());
        record1.setField(nvfield1.getName(), "nvpear");
        record1.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, record1.getId(), nvfield1.getId(), nvTag.getId());
        record1 = defaultTable.create(record1);

        Record record2 = defaultTable.newRecord();
        record2.setRecordType(nvRecordType1.getName());
        record2.setField(nvLinkField1.getName(), new Link(record1.getId()));
        record2.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, record2.getId(), nvLinkField1.getId(), nvTag.getId());
        record2 = defaultTable.create(record2);

        commitIndex();
        verifyResultCount("nv_deref1:nvpear", 1);
    }

    //
    // Variant deref
    //
    {
        log.debug("Begin test NV7");
        Record masterRecord = defaultTable.newRecord();
        masterRecord.setRecordType(nvRecordType1.getName());
        masterRecord.setField(nvfield1.getName(), "yellow");
        masterRecord.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, masterRecord.getId(), nvfield1.getId(), nvTag.getId());
        masterRecord = defaultTable.create(masterRecord);

        RecordId var1Id = idGenerator.newRecordId(masterRecord.getId(), Collections.singletonMap("lang", "en"));
        Record var1Record = defaultTable.newRecord(var1Id);
        var1Record.setRecordType(nvRecordType1.getName());
        var1Record.setField(nvfield1.getName(), "green");
        var1Record.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, var1Id, nvfield1.getId(), nvTag.getId());
        defaultTable.create(var1Record);

        Map<String, String> varProps = new HashMap<String, String>();
        varProps.put("lang", "en");
        varProps.put("branch", "dev");
        RecordId var2Id = idGenerator.newRecordId(masterRecord.getId(), varProps);
        Record var2Record = defaultTable.newRecord(var2Id);
        var2Record.setRecordType(nvRecordType1.getName());
        var2Record.setField(nvfield1.getName(), "blue");
        var2Record.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, var2Id, nvfield1.getId(), nvTag.getId());
        defaultTable.create(var2Record);

        commitIndex();
        verifyResultCount("nv_deref2:yellow", 1);
        verifyResultCount("nv_deref3:yellow", 2);
        verifyResultCount("nv_deref4:green", 1);
        verifyResultCount("nv_deref3:green", 0);
        verifyResultCount("nv_deref5:blue", 1);
        verifyResultCount("nv_deref5:green", 0);
        verifyResultCount("nv_deref5:yellow", 0);
        verifyResultCount("nv_deref6:blue", 2);
        verifyResultCount("nv_deref7:blue", 1);
        verifyResultCount("nv_deref8:blue", 0);
    }

    //
    // Update denormalized data
    //
    {
        log.debug("Begin test NV8");
        Record record1 = defaultTable.newRecord(idGenerator.newRecordId("boe"));
        record1.setRecordType(nvRecordType1.getName());
        record1.setField(nvfield1.getName(), "cucumber");
        record1.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, record1.getId(), nvfield1.getId(), nvTag.getId());
        record1 = defaultTable.create(record1);

        // Create a record which will contain denormalized data through linking
        Record record2 = defaultTable.newRecord();
        record2.setRecordType(nvRecordType1.getName());
        record2.setField(nvLinkField1.getName(), new Link(record1.getId()));
        record2.setField(nvfield1.getName(), "mushroom");
        record2.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, record2.getId(), nvLinkField1.getId(), nvfield1.getId(),
                nvTag.getId());
        record2 = defaultTable.create(record2);

        // Create a record which will contain denormalized data through master-dereferencing and forward-variant-dereferencing
        RecordId record3Id = idGenerator.newRecordId(record1.getId(), Collections.singletonMap("lang", "en"));
        Record record3 = defaultTable.newRecord(record3Id);
        record3.setRecordType(nvRecordType1.getName());
        record3.setField(nvfield1.getName(), "eggplant");
        record3.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, record3.getId(), nvfield1.getId(), nvTag.getId());
        record3 = defaultTable.create(record3);

        // Create a record which will contain denormalized data through variant-dereferencing
        Map<String, String> varprops = new HashMap<String, String>();
        varprops.put("lang", "en");
        varprops.put("branch", "dev");
        RecordId record4Id = idGenerator.newRecordId(record1.getId(), varprops);
        Record record4 = defaultTable.newRecord(record4Id);
        record4.setRecordType(nvRecordType1.getName());
        record4.setField(nvfield1.getName(), "broccoli");
        record4.setField(nvTag.getName(), 0L);
        expectEvent(CREATE, Table.RECORD.name, record4.getId(), nvfield1.getId(), nvTag.getId());
        record4 = defaultTable.create(record4);

        commitIndex();
        verifyResultCount("nv_deref1:cucumber", 1); // record2[nv:linkField1] = record1
        verifyResultCount("nv_deref2:cucumber", 1); // record4{-branch,-lang} = record1
        verifyResultCount("nv_deref3:cucumber", 2); // record3{master} and record4{master} = record1
        verifyResultCount("nv_deref4:eggplant", 1); // record4{-branch} = record3
        verifyResultCount("nv_deref5:broccoli", 1); // record3{+branch} = record4
        verifyResultCount("nv_deref6:broccoli", 2); // record1{+branch,+lang} = record4 (2 tags!)
        verifyResultCount("nv_deref7:broccoli", 1); // record3{+branch=dev} = record4

        // Update record1, check if the others are updated in the index
        log.debug("Begin test NV9");
        record1.setField(nvfield1.getName(), "tomato");
        expectEvent(UPDATE, Table.RECORD.name, record1.getId(), nvfield1.getId());
        record1 = defaultTable.update(record1);

        commitIndex();
        verifyResultCount("nv_deref1:tomato", 1); // record2[ns:nvLinkField1] = record1
        verifyResultCount("nv_deref2:tomato", 1); // record4{-branch,-lang} = record1
        verifyResultCount("nv_deref3:tomato", 2); // record3{master} and record4{master} = record1
        verifyResultCount("nv_deref1:cucumber", 0); // old value should be removed from index (non versioned field!)
        verifyResultCount("nv_deref2:cucumber", 0); // old value should be removed from index (non versioned field!)
        verifyResultCount("nv_deref3:cucumber", 0); // old value should be removed from index (non versioned field!)
        verifyResultCount("nv_deref4:eggplant", 1); // record4(-branch) = record3

        // Update record3, index for record4 should be updated
        log.debug("Begin test NV10");
        record3.setField(nvfield1.getName(), "courgette");
        expectEvent(UPDATE, Table.RECORD.name, record3.getId(), nvfield1.getId());
        defaultTable.update(record3);

        commitIndex();
        verifyResultCount("nv_deref4:courgette", 1); // record4(-branch) = record3
        verifyResultCount("nv_deref4:eggplant", 0); // old value should be removed from index (non versioned field!)

        // Update record4, index for record3 and record1 should be updated
        log.debug("Begin test NV10.1");
        record4.setField(nvfield1.getName(), "cauliflower"); //FIXME: 2nd courgette; use something else here
        expectEvent(UPDATE, Table.RECORD.name, record4.getId(), nvfield1.getId());
        defaultTable.update(record4);

        commitIndex();
        verifyResultCount("nv_deref5:cauliflower", 1); // record3{+branch} produces record4
        verifyResultCount("nv_deref5:broccoli", 0); // old value should be removed from index
        verifyResultCount("nv_deref5:courgette", 0); // sanity check, nothing could match
        verifyResultCount("nv_deref6:cauliflower", 2); // record1{+branch,+lang} = record4 (2 vtags!)
        verifyResultCount("nv_deref6:broccoli", 0); // old value should be removed from index
        verifyResultCount("nv_deref7:cauliflower", 1); // record3{+branch=dev} = record4
        verifyResultCount("nv_deref7:broccoli", 0); // old value should be removed from index

        // Delete record 3: index for record 4 should be updated
        log.debug("Begin test NV11");
        verifyResultCount("lily.id:" + ClientUtils.escapeQueryChars(record3.getId().toString()), 1);
        expectEvent(DELETE, Table.RECORD.name, record3.getId());
        defaultTable.delete(record3.getId());

        commitIndex();
        verifyResultCount("nv_deref4:cauliflower", 0);
        verifyResultCount("nv_deref3:tomato", 1);
        verifyResultCount("lily.id:" + ClientUtils.escapeQueryChars(record3.getId().toString()), 0);

        // Delete record 4
        log.debug("Begin test NV12");
        expectEvent(DELETE, Table.RECORD.name, record4.getId());
        defaultTable.delete(record4.getId());

        commitIndex();
        verifyResultCount("nv_deref3:tomato", 0);
        verifyResultCount("nv_field1:broccoli", 0);
        verifyResultCount("lily.id:" + ClientUtils.escapeQueryChars(record4.getId().toString()), 0);

        // Delete record 1: index of record 2 should be updated
        log.debug("Begin test NV13");
        expectEvent(DELETE, Table.RECORD.name, record1.getId());
        defaultTable.delete(record1.getId());

        commitIndex();
        verifyResultCount("nv_deref1:tomato", 0);
        verifyResultCount("nv_field1:mushroom", 1);
    }

    assertEquals("All received messages are correct.", 0, messageVerifier.getFailures());
}

From source file:org.lilyproject.indexer.engine.test.IndexerTest.java

License:Apache License

private static String qesc(String input) {
    return ClientUtils.escapeQueryChars(input);
}

From source file:org.opencastproject.archive.opencast.solr.SolrIndexManager.java

License:Educational Community License

/**
 * Set the deleted flag of all versions of the media package with the given id.
 * /*  w  w  w  . j a  va 2  s  . c om*/
 * @param id
 *          identifier of the series or episode to delete
 * @param deletionDate
 *          the deletion date
 * @throws SolrServerException
 *           if an errors occurs while talking to solr
 */
public boolean delete(String id, Date deletionDate) throws SolrServerException {
    try {
        // Load the existing episode
        QueryResponse solrResponse = null;
        try {
            SolrQuery query = new SolrQuery(Schema.DC_ID + ":" + ClientUtils.escapeQueryChars(id) + " AND "
                    + Schema.OC_DELETED + ":false");
            solrResponse = solrServer.query(query);
        } catch (Exception e1) {
            throw new SolrServerException(e1);
        }

        // Did we find the episode?
        if (solrResponse.getResults().size() == 0) {
            return false;
        }

        for (SolrDocument doc : solrResponse.getResults()) {
            // Use all existing fields
            SolrInputDocument inputDocument = new SolrInputDocument();
            for (String field : doc.getFieldNames()) {
                inputDocument.setField(field, doc.get(field));
            }

            // Set the oc_deleted field to true and the timestamp to the current date, then update
            Schema.setOcDeleted(inputDocument, true);
            Schema.setOcTimestamp(inputDocument, deletionDate);
            solrServer.add(inputDocument);
            solrServer.commit();
        }
        return true;
    } catch (IOException e) {
        throw new SolrServerException(e);
    }
}

From source file:org.opencastproject.episode.impl.solr.SolrIndexManager.java

License:Educational Community License

/**
 * Set the deleted flag of all versions of the media package with the given id.
 * //from w ww  .  ja v  a2 s . c  o m
 * @param id
 *          identifier of the series or episode to delete
 * @param deletionDate
 *          the deletion date
 * @throws SolrServerException
 *           if an errors occurs while talking to solr
 */
public boolean delete(String id, Date deletionDate) throws SolrServerException {
    try {
        // Load the existing episode
        QueryResponse solrResponse = null;
        try {
            SolrQuery query = new SolrQuery(Schema.DC_ID + ":" + ClientUtils.escapeQueryChars(id) + " AND -"
                    + Schema.OC_DELETED + ":[* TO *]");
            solrResponse = solrServer.query(query);
        } catch (Exception e1) {
            throw new SolrServerException(e1);
        }

        // Did we find the episode?
        if (solrResponse.getResults().size() == 0) {
            return false;
        }

        for (SolrDocument doc : solrResponse.getResults()) {
            // Use all existing fields
            SolrInputDocument inputDocument = new SolrInputDocument();
            for (String field : doc.getFieldNames()) {
                inputDocument.setField(field, doc.get(field));
            }

            // Set the oc_deleted field to the current date, then update
            Schema.setOcDeleted(inputDocument, deletionDate);
            solrServer.add(inputDocument);
            solrServer.commit();
        }
        return true;
    } catch (IOException e) {
        throw new SolrServerException(e);
    }
}

From source file:org.opencastproject.episode.impl.solr.SolrIndexManager.java

License:Educational Community License

/** Set the "locked" flag of an index entry. */
public boolean setLocked(String id, boolean locked) throws SolrServerException {
    try {/*from   w w w.jav  a 2 s.c o m*/
        // Load the existing episode
        QueryResponse solrResponse = null;
        try {
            SolrQuery query = new SolrQuery(Schema.DC_ID + ":" + ClientUtils.escapeQueryChars(id));
            // + " AND -" + Schema.OC_DELETED + ":[* TO *]"
            // + " AND " + Schema.OC_LOCKED + ":" + (!locked));
            solrResponse = solrServer.query(query);
        } catch (Exception e) {
            throw new SolrServerException(e);
        }

        // Did we find the episode?
        if (solrResponse.getResults().size() == 0) {
            return false;
        }

        // Use all existing fields
        for (SolrDocument doc : solrResponse.getResults()) {
            SolrInputDocument inputDocument = new SolrInputDocument();
            for (String field : doc.getFieldNames()) {
                inputDocument.setField(field, doc.get(field));
            }

            solrServer.add(inputDocument);
            solrServer.commit();
        }
        return true;
    } catch (IOException e) {
        throw new SolrServerException(e);
    }
}

From source file:org.opencastproject.episode.impl.solr.SolrIndexManager.java

License:Educational Community License

/** Set the "latestVersion" flag of an index entry. */
private void resetFormerLatestVersion(MediaPackage sourceMediaPackage, Version version)
        throws SolrServerException, IOException {
    final SolrQuery query = new SolrQuery(Schema.ID + ":"
            + ClientUtils.escapeQueryChars(sourceMediaPackage.getIdentifier() + version.toString()));
    QueryResponse response = solrServer.query(query);

    // Did we find the episode?
    if (response.getResults().size() == 0)
        return;/*  www  .  j  a  v  a 2 s.  c  o m*/

    if (response.getResults().size() > 1)
        throw new SolrServerException("Multiple values with the same unique identifier found!");

    SolrDocument doc = response.getResults().get(0);
    SolrInputDocument inputDoc = new SolrInputDocument();
    for (String field : doc.getFieldNames()) {
        inputDoc.setField(field, doc.get(field));
    }
    Schema.setOcLatestVersion(inputDoc, false);
    solrServer.add(inputDoc);
}

From source file:org.opencastproject.episode.impl.solr.SolrRequester.java

License:Educational Community License

/**
 * Converts the query object into a solr query and returns the results.
 * /*  w w  w.  j av  a2  s  .c om*/
 * @param q
 *          the query
 * @return the search results
 */
private SolrQuery createQuery(EpisodeQuery q) throws SolrServerException {
    final StringBuilder sb = new StringBuilder();
    for (String solrQueryRequest : q.getQuery())
        sb.append(solrQueryRequest);
    append(sb, Schema.DC_ID, q.getId());

    // full text query with boost
    for (String solrTextRequest : q.getText()) {
        if (sb.length() > 0)
            sb.append(" AND ");
        sb.append("(").append(createBoostedFullTextQuery(solrTextRequest)).append(")");
    }

    appendFuzzy(sb, Schema.DC_CREATOR_SUM, q.getCreator());
    appendFuzzy(sb, Schema.DC_CONTRIBUTOR_SUM, q.getContributor());
    append(sb, Schema.DC_LANGUAGE, q.getLanguage());
    appendFuzzy(sb, Schema.DC_LICENSE_SUM, q.getLicense());
    appendFuzzy(sb, Schema.DC_TITLE_SUM, q.getTitle());
    appendFuzzy(sb, Schema.S_DC_TITLE_SUM, q.getSeriesTitle());
    append(sb, Schema.DC_IS_PART_OF, q.getSeriesId());
    append(sb, Schema.OC_ORGANIZATION, q.getOrganization());

    if (q.getElementTags().size() > 0) {
        if (sb.length() > 0)
            sb.append(" AND ");
        StringBuilder tagBuilder = new StringBuilder();
        for (String tag : mlist(q.getElementTags()).bind(Options.<String>asList().o(SolrUtils.clean))) {
            if (tagBuilder.length() == 0) {
                tagBuilder.append("(");
            } else {
                tagBuilder.append(" OR ");
            }
            tagBuilder.append(Schema.OC_ELEMENTTAGS);
            tagBuilder.append(":");
            tagBuilder.append(SolrUtils.clean(tag));
        }
        if (tagBuilder.length() > 0) {
            tagBuilder.append(") ");
            sb.append(tagBuilder);
        }
    }
    if (q.getElementFlavors().size() > 0) {
        if (sb.length() > 0)
            sb.append(" AND ");
        StringBuilder flavorBuilder = new StringBuilder();
        for (String flavor : mlist(q.getElementFlavors()).bind(Options.<String>asList().o(SolrUtils.clean)
                .o(Strings.<MediaPackageElementFlavor>asStringNull()))) {
            if (flavorBuilder.length() == 0) {
                flavorBuilder.append("(");
            } else {
                flavorBuilder.append(" OR ");
            }
            flavorBuilder.append(Schema.OC_ELEMENTFLAVORS);
            flavorBuilder.append(":");
            flavorBuilder.append(ClientUtils.escapeQueryChars(flavor));
        }
        if (flavorBuilder.length() > 0) {
            flavorBuilder.append(") ");
            sb.append(flavorBuilder);
        }
    }
    for (Date deleted : q.getDeletedDate()) {
        if (sb.length() > 0)
            sb.append(" AND ");
        sb.append(Schema.OC_DELETED).append(":")
                .append(SolrUtils.serializeDateRange(option(deleted), Option.<Date>none()));
    }
    if (!q.getIncludeDeleted()) {
        if (sb.length() > 0)
            sb.append(" AND ");
        sb.append("-" + Schema.OC_DELETED + ":[* TO *]");
    }

    if (q.getOnlyLastVersion()) {
        if (sb.length() > 0)
            sb.append(" AND ");
        sb.append(Schema.OC_LATEST_VERSION + ":true");
    }

    // only episodes
    if (sb.length() > 0)
        sb.append(" AND ");
    sb.append(Schema.OC_MEDIATYPE + ":" + SearchResultItem.SearchResultItemType.AudioVisual);

    // only add date range if at least on criteria is set
    if (q.getAddedBefore().isSome() || q.getAddedAfter().isSome()) {
        if (sb.length() > 0)
            sb.append(" AND ");
        sb.append(Schema.OC_TIMESTAMP + ":[" + q.getAddedAfter().map(SolrUtils.serializeDate).getOrElse("*")
                + " TO " + q.getAddedBefore().map(SolrUtils.serializeDate).getOrElse("*") + "]");
    }

    if (sb.length() == 0)
        sb.append("*:*");

    final SolrQuery solr = new SolrQuery(sb.toString());
    // limit & offset
    solr.setRows(q.getLimit());
    solr.setStart(q.getOffset());

    // sorting
    final SolrQuery.ORDER order = q.getSortAscending() ? SolrQuery.ORDER.asc : SolrQuery.ORDER.desc;
    solr.addSortField(getSortField(q.getSort()), order);

    solr.setFields("* score");

    return solr;
}

From source file:org.opencastproject.scheduler.impl.solr.SchedulerServiceSolrIndex.java

License:Educational Community License

/**
 * Retrieves SolrDocument by specified ID. If such document does not exist, null is returned.
 * /*from ww w  .jav a  2 s. c  o  m*/
 * @param id
 *          ID of document to be retrieved
 * @return matching SolrDocument or null
 * @throws SchedulerServiceDatabaseException
 *           if exception occurred
 */
private SolrDocument retrieveDocumentById(long id) throws SchedulerServiceDatabaseException {
    String solrQueryString = SolrFields.ID_KEY + ":" + ClientUtils.escapeQueryChars(Long.toString(id));
    SolrQuery q = new SolrQuery(solrQueryString);
    QueryResponse response;
    try {
        response = solrServer.query(q);
    } catch (SolrServerException e) {
        logger.error("Could not perform event retrieval: {}", e);
        throw new SchedulerServiceDatabaseException(e);
    }
    return response.getResults().isEmpty() ? null : response.getResults().get(0);
}

From source file:org.opencastproject.scheduler.impl.solr.SchedulerServiceSolrIndex.java

License:Educational Community License

/**
 * Appends query parameters to a solr query
 * //w  w w  . j  ava 2s .  co  m
 * @param sb
 *          The {@link StringBuilder} containing the query
 * @param key
 *          the key for this search parameter
 * @param value
 *          the value for this search parameter
 * @return the appended {@link StringBuilder}
 */
private StringBuilder append(StringBuilder sb, String key, String value) {
    if (StringUtils.isBlank(key) || StringUtils.isBlank(value)) {
        return sb;
    }
    if (sb.length() > 0) {
        sb.append(" AND ");
    }
    sb.append(key);
    sb.append(":");
    sb.append(ClientUtils.escapeQueryChars(value));
    return sb;
}