Remoting should support 'who extends/overrides/implements me' query.
authorJan Lahoda <jlahoda@netbeans.org>
Thu, 07 Jul 2011 09:13:19 +0200
changeset 626a318387d41a4
parent 625 f7e813947ce3
child 627 cc7cae86b073
Remoting should support 'who extends/overrides/implements me' query.
remoting/server/indexer/usages/src/org/netbeans/modules/jackpot30/indexer/usages/IndexerImpl.java
remoting/server/web/type.web.api/src/org/netbeans/modules/jackpot30/backend/type/api/Base.java
remoting/server/web/usages.web.api/nbproject/project.properties
remoting/server/web/usages.web.api/src/org/netbeans/modules/jackpot30/backend/usages/api/API.java
remoting/server/web/usages.web.api/src/org/netbeans/modules/jackpot30/backend/usages/api/SubClasses.java
remoting/server/web/usages.web.api/src/org/netbeans/modules/jackpot30/backend/usages/api/Usages.java
     1.1 --- a/remoting/server/indexer/usages/src/org/netbeans/modules/jackpot30/indexer/usages/IndexerImpl.java	Wed Jul 06 11:39:05 2011 +0200
     1.2 +++ b/remoting/server/indexer/usages/src/org/netbeans/modules/jackpot30/indexer/usages/IndexerImpl.java	Thu Jul 07 09:13:19 2011 +0200
     1.3 @@ -48,10 +48,12 @@
     1.4  import com.sun.source.tree.VariableTree;
     1.5  import com.sun.source.util.TreePathScanner;
     1.6  import java.io.IOException;
     1.7 +import java.util.Arrays;
     1.8  import java.util.Collection;
     1.9  import java.util.Collections;
    1.10  import java.util.HashSet;
    1.11  import java.util.LinkedList;
    1.12 +import java.util.List;
    1.13  import java.util.Set;
    1.14  import javax.lang.model.element.Element;
    1.15  import javax.lang.model.element.ElementKind;
    1.16 @@ -161,8 +163,8 @@
    1.17                                      }
    1.18  
    1.19                                      if (el.getKind() == ElementKind.METHOD) {
    1.20 -                                        while ((el = cc.getElementUtilities().getOverriddenMethod((ExecutableElement) el)) != null) {
    1.21 -                                            serialized = Common.serialize(ElementHandle.create(el));
    1.22 +                                        for (ExecutableElement e : overrides(cc, (ExecutableElement) el)) {
    1.23 +                                            serialized = Common.serialize(ElementHandle.create(e));
    1.24  
    1.25                                              if (SEEN_SIGNATURES.add(serialized)) {
    1.26                                                  usages.add(new Field(KEY_SIGNATURES, serialized, Store.YES, Index.NOT_ANALYZED));
    1.27 @@ -182,12 +184,16 @@
    1.28  
    1.29                                      if (el != null) {
    1.30                                          try {
    1.31 -                                            currentClassFQN = cc.getElements().getBinaryName((TypeElement) el).toString();
    1.32 +                                            TypeElement tel = (TypeElement) el;
    1.33 +                                            currentClassFQN = cc.getElements().getBinaryName(tel).toString();
    1.34                                              Document currentClassDocument = new Document();
    1.35  
    1.36                                              currentClassDocument.add(new Field("classFQN", currentClassFQN, Store.YES, Index.NO));
    1.37                                              currentClassDocument.add(new Field("classSimpleName", node.getSimpleName().toString(), Store.YES, Index.NOT_ANALYZED));
    1.38                                              currentClassDocument.add(new Field("classSimpleNameLower", node.getSimpleName().toString().toLowerCase(), Store.YES, Index.NOT_ANALYZED));
    1.39 +
    1.40 +                                            recordSuperTypes(currentClassDocument, tel, new HashSet<String>(Arrays.asList(tel.getQualifiedName().toString())));
    1.41 +
    1.42                                              currentClassDocument.add(new Field("file", file, Store.YES, Index.NO));
    1.43  
    1.44                                              IndexAccessor.getCurrent().getIndexWriter().addDocument(currentClassDocument);
    1.45 @@ -247,6 +253,10 @@
    1.46                                              
    1.47                                              currentFeatureDocument.add(new Field("featureSignature", featureSignature, Store.YES, Index.NO));
    1.48                                              currentFeatureDocument.add(new Field("featureVMSignature", ClassFileUtil.createExecutableDescriptor((ExecutableElement) el)[2], Store.YES, Index.NO));
    1.49 +
    1.50 +                                            for (ExecutableElement e : overrides(cc, (ExecutableElement) el)) {
    1.51 +                                                currentFeatureDocument.add(new Field("featureOverrides", Common.serialize(ElementHandle.create(e)), Store.YES, Index.NOT_ANALYZED));
    1.52 +                                            }
    1.53                                          }
    1.54  
    1.55                                          IndexAccessor.getCurrent().getIndexWriter().addDocument(currentFeatureDocument);
    1.56 @@ -268,6 +278,35 @@
    1.57          }
    1.58      }
    1.59  
    1.60 +    private static Iterable<? extends ExecutableElement> overrides(CompilationInfo info, ExecutableElement method) {
    1.61 +        List<ExecutableElement> result = new LinkedList<ExecutableElement>();
    1.62 +
    1.63 +        //XXX: one method may override+implement more than one method
    1.64 +        while ((method = info.getElementUtilities().getOverriddenMethod(method)) != null) {
    1.65 +            result.add(method);
    1.66 +        }
    1.67 +
    1.68 +        return result;
    1.69 +    }
    1.70 +    
    1.71 +    private static void recordSuperTypes(Document target, TypeElement tel, Set<String> alreadySeen) {
    1.72 +        String fqn = tel.getQualifiedName().toString();
    1.73 +
    1.74 +        if (alreadySeen.add(fqn)) {
    1.75 +            target.add(new Field("classSupertypes", fqn, Store.YES, Index.NOT_ANALYZED));
    1.76 +        }
    1.77 +
    1.78 +        if (tel.getSuperclass().getKind() == TypeKind.DECLARED) {
    1.79 +            recordSuperTypes(target, (TypeElement) ((DeclaredType) tel.getSuperclass()).asElement(), alreadySeen);
    1.80 +        }
    1.81 +
    1.82 +        for (TypeMirror i : tel.getInterfaces()) {
    1.83 +            if (i.getKind() == TypeKind.DECLARED) {
    1.84 +                recordSuperTypes(target, (TypeElement) ((DeclaredType) i).asElement(), alreadySeen);
    1.85 +            }
    1.86 +        }
    1.87 +    }
    1.88 +
    1.89      private static void encodeTypeParameters(CompilationInfo info, Collection<? extends TypeParameterElement> params, StringBuilder result) {
    1.90          if (params.isEmpty()) return;
    1.91          result.append("<");
     2.1 --- a/remoting/server/web/type.web.api/src/org/netbeans/modules/jackpot30/backend/type/api/Base.java	Wed Jul 06 11:39:05 2011 +0200
     2.2 +++ b/remoting/server/web/type.web.api/src/org/netbeans/modules/jackpot30/backend/type/api/Base.java	Thu Jul 07 09:13:19 2011 +0200
     2.3 @@ -50,6 +50,7 @@
     2.4  import org.apache.lucene.search.Query;
     2.5  import org.codeviation.pojson.Pojson;
     2.6  import org.netbeans.modules.jackpot30.backend.base.CategoryStorage;
     2.7 +import org.netbeans.modules.jackpot30.backend.base.Utilities;
     2.8  import org.netbeans.modules.jumpto.type.GoToTypeAction;
     2.9  import org.netbeans.modules.parsing.lucene.support.Convertor;
    2.10  import org.netbeans.modules.parsing.lucene.support.Index;
    2.11 @@ -102,7 +103,6 @@
    2.12              }
    2.13          }
    2.14  
    2.15 -        Map<String, List<T>> result = new LinkedHashMap<String, List<T>>();
    2.16          CategoryStorage category = CategoryStorage.forId(segment);
    2.17          Index index = category.getIndex();
    2.18  
    2.19 @@ -119,21 +119,7 @@
    2.20          //TODO: field selector:
    2.21          index.query(found, conv, null, new AtomicBoolean(), queries.toArray(new Query[queries.size()]));
    2.22  
    2.23 -        for (Entry<String, T> e : found) {
    2.24 -            for (String rel : category.getSourceRoots()) {
    2.25 -                if (e.getKey().startsWith(rel)) {
    2.26 -                    List<T> current = result.get(rel);
    2.27 -
    2.28 -                    if (current == null) {
    2.29 -                        result.put(rel, current = new ArrayList<T>());
    2.30 -                    }
    2.31 -
    2.32 -                    current.add(e.getValue());
    2.33 -                }
    2.34 -            }
    2.35 -        }
    2.36 -
    2.37 -        return Pojson.save(result);
    2.38 +        return Pojson.save(Utilities.sortBySourceRoot(found, category));
    2.39      }
    2.40  
    2.41  }
     3.1 --- a/remoting/server/web/usages.web.api/nbproject/project.properties	Wed Jul 06 11:39:05 2011 +0200
     3.2 +++ b/remoting/server/web/usages.web.api/nbproject/project.properties	Thu Jul 07 09:13:19 2011 +0200
     3.3 @@ -28,6 +28,8 @@
     3.4  file.reference.org-netbeans-modules-parsing-api.jar=../../../../server/lib/org-netbeans-modules-parsing-api.jar
     3.5  file.reference.org-netbeans-modules-parsing-lucene.jar=../../../../server/lib/org-netbeans-modules-parsing-lucene.jar
     3.6  file.reference.org-openide-filesystems.jar=../../../../server/lib/org-openide-filesystems.jar
     3.7 +file.reference.util-commons.jar=../../../ide/api/external/util-commons.jar
     3.8 +file.reference.util-pojson.jar=../../../ide/api/external/util-pojson.jar
     3.9  includes=**
    3.10  jar.compress=false
    3.11  javac.classpath=\
    3.12 @@ -36,7 +38,9 @@
    3.13      ${reference.base_web_api.jar}:\
    3.14      ${file.reference.org-netbeans-modules-parsing-api.jar}:\
    3.15      ${file.reference.org-openide-filesystems.jar}:\
    3.16 -    ${file.reference.org-netbeans-modules-parsing-lucene.jar}
    3.17 +    ${file.reference.org-netbeans-modules-parsing-lucene.jar}:\
    3.18 +    ${file.reference.util-commons.jar}:\
    3.19 +    ${file.reference.util-pojson.jar}
    3.20  # Space-separated list of extra javac options
    3.21  javac.compilerargs=
    3.22  javac.deprecation=false
     4.1 --- a/remoting/server/web/usages.web.api/src/org/netbeans/modules/jackpot30/backend/usages/api/API.java	Wed Jul 06 11:39:05 2011 +0200
     4.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.3 @@ -1,95 +0,0 @@
     4.4 -/*
     4.5 - * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
     4.6 - *
     4.7 - * Copyright 2011 Oracle and/or its affiliates. All rights reserved.
     4.8 - *
     4.9 - * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
    4.10 - * Other names may be trademarks of their respective owners.
    4.11 - *
    4.12 - * The contents of this file are subject to the terms of either the GNU
    4.13 - * General Public License Version 2 only ("GPL") or the Common
    4.14 - * Development and Distribution License("CDDL") (collectively, the
    4.15 - * "License"). You may not use this file except in compliance with the
    4.16 - * License. You can obtain a copy of the License at
    4.17 - * http://www.netbeans.org/cddl-gplv2.html
    4.18 - * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
    4.19 - * specific language governing permissions and limitations under the
    4.20 - * License.  When distributing the software, include this License Header
    4.21 - * Notice in each file and include the License file at
    4.22 - * nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
    4.23 - * particular file as subject to the "Classpath" exception as provided
    4.24 - * by Oracle in the GPL Version 2 section of the License file that
    4.25 - * accompanied this code. If applicable, add the following below the
    4.26 - * License Header, with the fields enclosed by brackets [] replaced by
    4.27 - * your own identifying information:
    4.28 - * "Portions Copyrighted [year] [name of copyright owner]"
    4.29 - *
    4.30 - * If you wish your version of this file to be governed by only the CDDL
    4.31 - * or only the GPL Version 2, indicate your decision by adding
    4.32 - * "[Contributor] elects to include this software in this distribution
    4.33 - * under the [CDDL or GPL Version 2] license." If you do not indicate a
    4.34 - * single choice of license, a recipient has the option to distribute
    4.35 - * your version of this file under either the CDDL, the GPL Version 2 or
    4.36 - * to extend the choice of license to its licensees as provided above.
    4.37 - * However, if you add GPL Version 2 code and therefore, elected the GPL
    4.38 - * Version 2 license, then the option applies only if the new code is
    4.39 - * made subject to such option by the copyright holder.
    4.40 - *
    4.41 - * Contributor(s):
    4.42 - *
    4.43 - * Portions Copyrighted 2011 Sun Microsystems, Inc.
    4.44 - */
    4.45 -package org.netbeans.modules.jackpot30.backend.usages.api;
    4.46 -
    4.47 -import java.io.IOException;
    4.48 -import java.util.ArrayList;
    4.49 -import java.util.List;
    4.50 -import java.util.concurrent.atomic.AtomicBoolean;
    4.51 -import javax.ws.rs.GET;
    4.52 -import javax.ws.rs.Path;
    4.53 -import javax.ws.rs.Produces;
    4.54 -import javax.ws.rs.QueryParam;
    4.55 -import org.apache.lucene.document.Document;
    4.56 -import org.apache.lucene.search.Query;
    4.57 -import org.netbeans.modules.jackpot30.backend.base.CategoryStorage;
    4.58 -import org.netbeans.modules.parsing.lucene.support.Convertor;
    4.59 -import org.netbeans.modules.parsing.lucene.support.Index;
    4.60 -import org.netbeans.modules.parsing.lucene.support.Queries;
    4.61 -import org.netbeans.modules.parsing.lucene.support.Queries.QueryKind;
    4.62 -
    4.63 -/**
    4.64 - *
    4.65 - * @author lahvac
    4.66 - */
    4.67 -@Path("/index/usages")
    4.68 -public class API {
    4.69 -
    4.70 -    private static final String KEY_SIGNATURES = "signatures";
    4.71 -    
    4.72 -    @GET
    4.73 -    @Path("/search")
    4.74 -    @Produces("text/plain")
    4.75 -    public String search(@QueryParam("path") String segment, @QueryParam("signatures") String signatures) throws IOException, InterruptedException {
    4.76 -        StringBuilder result = new StringBuilder();
    4.77 -        CategoryStorage category = CategoryStorage.forId(segment);
    4.78 -        Index idx = category.getIndex();
    4.79 -        Query query = Queries.createQuery(KEY_SIGNATURES, "does-not-exist", signatures, QueryKind.EXACT);
    4.80 -        List<String> found = new ArrayList<String>();
    4.81 -
    4.82 -        //TODO: field selector:
    4.83 -        idx.query(found, new ConvertorImpl(), null, new AtomicBoolean(), query);
    4.84 -
    4.85 -        for (String foundFile : found) {
    4.86 -            result.append(foundFile);
    4.87 -            result.append("\n");
    4.88 -        }
    4.89 -
    4.90 -        return result.toString();
    4.91 -    }
    4.92 -
    4.93 -    private static class ConvertorImpl implements Convertor<Document, String> {
    4.94 -        @Override public String convert(Document p) {
    4.95 -            return p.get("file");
    4.96 -        }
    4.97 -    }
    4.98 -}
     5.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     5.2 +++ b/remoting/server/web/usages.web.api/src/org/netbeans/modules/jackpot30/backend/usages/api/SubClasses.java	Thu Jul 07 09:13:19 2011 +0200
     5.3 @@ -0,0 +1,120 @@
     5.4 +/*
     5.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
     5.6 + *
     5.7 + * Copyright 2011 Oracle and/or its affiliates. All rights reserved.
     5.8 + *
     5.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
    5.10 + * Other names may be trademarks of their respective owners.
    5.11 + *
    5.12 + * The contents of this file are subject to the terms of either the GNU
    5.13 + * General Public License Version 2 only ("GPL") or the Common
    5.14 + * Development and Distribution License("CDDL") (collectively, the
    5.15 + * "License"). You may not use this file except in compliance with the
    5.16 + * License. You can obtain a copy of the License at
    5.17 + * http://www.netbeans.org/cddl-gplv2.html
    5.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
    5.19 + * specific language governing permissions and limitations under the
    5.20 + * License.  When distributing the software, include this License Header
    5.21 + * Notice in each file and include the License file at
    5.22 + * nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
    5.23 + * particular file as subject to the "Classpath" exception as provided
    5.24 + * by Oracle in the GPL Version 2 section of the License file that
    5.25 + * accompanied this code. If applicable, add the following below the
    5.26 + * License Header, with the fields enclosed by brackets [] replaced by
    5.27 + * your own identifying information:
    5.28 + * "Portions Copyrighted [year] [name of copyright owner]"
    5.29 + *
    5.30 + * If you wish your version of this file to be governed by only the CDDL
    5.31 + * or only the GPL Version 2, indicate your decision by adding
    5.32 + * "[Contributor] elects to include this software in this distribution
    5.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
    5.34 + * single choice of license, a recipient has the option to distribute
    5.35 + * your version of this file under either the CDDL, the GPL Version 2 or
    5.36 + * to extend the choice of license to its licensees as provided above.
    5.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
    5.38 + * Version 2 license, then the option applies only if the new code is
    5.39 + * made subject to such option by the copyright holder.
    5.40 + *
    5.41 + * Contributor(s):
    5.42 + *
    5.43 + * Portions Copyrighted 2011 Sun Microsystems, Inc.
    5.44 + */
    5.45 +package org.netbeans.modules.jackpot30.backend.usages.api;
    5.46 +
    5.47 +import java.io.IOException;
    5.48 +import java.util.AbstractMap.SimpleEntry;
    5.49 +import java.util.ArrayList;
    5.50 +import java.util.HashMap;
    5.51 +import java.util.List;
    5.52 +import java.util.Map;
    5.53 +import java.util.Map.Entry;
    5.54 +import java.util.concurrent.atomic.AtomicBoolean;
    5.55 +import javax.ws.rs.GET;
    5.56 +import javax.ws.rs.Path;
    5.57 +import javax.ws.rs.Produces;
    5.58 +import javax.ws.rs.QueryParam;
    5.59 +import org.apache.lucene.document.Document;
    5.60 +import org.apache.lucene.search.Query;
    5.61 +import org.codeviation.pojson.Pojson;
    5.62 +import org.netbeans.modules.jackpot30.backend.base.CategoryStorage;
    5.63 +import org.netbeans.modules.jackpot30.backend.base.Utilities;
    5.64 +import org.netbeans.modules.parsing.lucene.support.Convertor;
    5.65 +import org.netbeans.modules.parsing.lucene.support.Index;
    5.66 +import org.netbeans.modules.parsing.lucene.support.Queries;
    5.67 +import org.netbeans.modules.parsing.lucene.support.Queries.QueryKind;
    5.68 +
    5.69 +/**
    5.70 + *
    5.71 + * @author lahvac
    5.72 + */
    5.73 +@Path("/index/implements")
    5.74 +public class SubClasses {
    5.75 +
    5.76 +    private static final String KEY_SUPERTYPES = "classSupertypes";
    5.77 +    
    5.78 +    @GET
    5.79 +    @Path("/search")
    5.80 +    @Produces("text/plain")
    5.81 +    public String search(@QueryParam("path") String segment, @QueryParam("type") String type, @QueryParam("method") String method) throws IOException, InterruptedException {
    5.82 +        CategoryStorage category = CategoryStorage.forId(segment);
    5.83 +        Index idx = category.getIndex();
    5.84 +        Query query = Queries.createQuery(type != null ? KEY_SUPERTYPES : "featureOverrides", "does-not-exist", type != null ? type : method, QueryKind.EXACT);
    5.85 +        List<Entry<String, Map<String, Object>>> found = new ArrayList<Entry<String, Map<String, Object>>>();
    5.86 +
    5.87 +        //TODO: field selector:
    5.88 +        idx.query(found, type != null ? new SubTypeConvertorImpl() : new OverridersConvertorImpl(), null, new AtomicBoolean(), query);
    5.89 +
    5.90 +        return Pojson.save(Utilities.sortBySourceRoot(found, category));
    5.91 +    }
    5.92 +
    5.93 +    private static class SubTypeConvertorImpl implements Convertor<Document, Entry<String, Map<String, Object>>> {
    5.94 +        @Override public Entry<String, Map<String, Object>> convert(Document p) {
    5.95 +            Map<String, Object> result = new HashMap<String, Object>();
    5.96 +
    5.97 +            result.put("file", p.get("file"));
    5.98 +            result.put("class", p.get("classFQN"));
    5.99 +
   5.100 +            return new SimpleEntry<String, Map<String, Object>>(p.get("file"), result);
   5.101 +        }
   5.102 +    }
   5.103 +
   5.104 +    private static class OverridersConvertorImpl implements Convertor<Document, Entry<String, Map<String, Object>>> {
   5.105 +        @Override public Entry<String, Map<String, Object>> convert(Document p) {
   5.106 +            Map<String, Object> result = new HashMap<String, Object>();
   5.107 +
   5.108 +            result.put("file", p.get("file"));
   5.109 +            result.put("enclosingFQN", p.get("featureClassFQN"));
   5.110 +            result.put("simpleName", p.get("featureSimpleName"));
   5.111 +            String featureSignature = p.get("featureSignature");
   5.112 +            if (featureSignature != null)
   5.113 +                result.put("signature", featureSignature);
   5.114 +            String featureVMSignature = p.get("featureVMSignature");
   5.115 +            if (featureVMSignature != null)
   5.116 +                result.put("vmsignature", featureVMSignature);
   5.117 +            result.put("kind", p.get("featureKind"));
   5.118 +            result.put("modifiers", p.getValues("featureModifiers")); //XXX
   5.119 +
   5.120 +            return new SimpleEntry<String, Map<String, Object>>(p.get("file"), result);
   5.121 +        }
   5.122 +    }
   5.123 +}
     6.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     6.2 +++ b/remoting/server/web/usages.web.api/src/org/netbeans/modules/jackpot30/backend/usages/api/Usages.java	Thu Jul 07 09:13:19 2011 +0200
     6.3 @@ -0,0 +1,95 @@
     6.4 +/*
     6.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
     6.6 + *
     6.7 + * Copyright 2011 Oracle and/or its affiliates. All rights reserved.
     6.8 + *
     6.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
    6.10 + * Other names may be trademarks of their respective owners.
    6.11 + *
    6.12 + * The contents of this file are subject to the terms of either the GNU
    6.13 + * General Public License Version 2 only ("GPL") or the Common
    6.14 + * Development and Distribution License("CDDL") (collectively, the
    6.15 + * "License"). You may not use this file except in compliance with the
    6.16 + * License. You can obtain a copy of the License at
    6.17 + * http://www.netbeans.org/cddl-gplv2.html
    6.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
    6.19 + * specific language governing permissions and limitations under the
    6.20 + * License.  When distributing the software, include this License Header
    6.21 + * Notice in each file and include the License file at
    6.22 + * nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
    6.23 + * particular file as subject to the "Classpath" exception as provided
    6.24 + * by Oracle in the GPL Version 2 section of the License file that
    6.25 + * accompanied this code. If applicable, add the following below the
    6.26 + * License Header, with the fields enclosed by brackets [] replaced by
    6.27 + * your own identifying information:
    6.28 + * "Portions Copyrighted [year] [name of copyright owner]"
    6.29 + *
    6.30 + * If you wish your version of this file to be governed by only the CDDL
    6.31 + * or only the GPL Version 2, indicate your decision by adding
    6.32 + * "[Contributor] elects to include this software in this distribution
    6.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
    6.34 + * single choice of license, a recipient has the option to distribute
    6.35 + * your version of this file under either the CDDL, the GPL Version 2 or
    6.36 + * to extend the choice of license to its licensees as provided above.
    6.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
    6.38 + * Version 2 license, then the option applies only if the new code is
    6.39 + * made subject to such option by the copyright holder.
    6.40 + *
    6.41 + * Contributor(s):
    6.42 + *
    6.43 + * Portions Copyrighted 2011 Sun Microsystems, Inc.
    6.44 + */
    6.45 +package org.netbeans.modules.jackpot30.backend.usages.api;
    6.46 +
    6.47 +import java.io.IOException;
    6.48 +import java.util.ArrayList;
    6.49 +import java.util.List;
    6.50 +import java.util.concurrent.atomic.AtomicBoolean;
    6.51 +import javax.ws.rs.GET;
    6.52 +import javax.ws.rs.Path;
    6.53 +import javax.ws.rs.Produces;
    6.54 +import javax.ws.rs.QueryParam;
    6.55 +import org.apache.lucene.document.Document;
    6.56 +import org.apache.lucene.search.Query;
    6.57 +import org.netbeans.modules.jackpot30.backend.base.CategoryStorage;
    6.58 +import org.netbeans.modules.parsing.lucene.support.Convertor;
    6.59 +import org.netbeans.modules.parsing.lucene.support.Index;
    6.60 +import org.netbeans.modules.parsing.lucene.support.Queries;
    6.61 +import org.netbeans.modules.parsing.lucene.support.Queries.QueryKind;
    6.62 +
    6.63 +/**
    6.64 + *
    6.65 + * @author lahvac
    6.66 + */
    6.67 +@Path("/index/usages")
    6.68 +public class Usages {
    6.69 +
    6.70 +    private static final String KEY_SIGNATURES = "signatures";
    6.71 +    
    6.72 +    @GET
    6.73 +    @Path("/search")
    6.74 +    @Produces("text/plain")
    6.75 +    public String search(@QueryParam("path") String segment, @QueryParam("signatures") String signatures) throws IOException, InterruptedException {
    6.76 +        StringBuilder result = new StringBuilder();
    6.77 +        CategoryStorage category = CategoryStorage.forId(segment);
    6.78 +        Index idx = category.getIndex();
    6.79 +        Query query = Queries.createQuery(KEY_SIGNATURES, "does-not-exist", signatures, QueryKind.EXACT);
    6.80 +        List<String> found = new ArrayList<String>();
    6.81 +
    6.82 +        //TODO: field selector:
    6.83 +        idx.query(found, new ConvertorImpl(), null, new AtomicBoolean(), query);
    6.84 +
    6.85 +        for (String foundFile : found) {
    6.86 +            result.append(foundFile);
    6.87 +            result.append("\n");
    6.88 +        }
    6.89 +
    6.90 +        return result.toString();
    6.91 +    }
    6.92 +
    6.93 +    private static class ConvertorImpl implements Convertor<Document, String> {
    6.94 +        @Override public String convert(Document p) {
    6.95 +            return p.get("file");
    6.96 +        }
    6.97 +    }
    6.98 +}