Package com.esri.gpt.control.georss

Source Code of com.esri.gpt.control.georss.ExtJsonFeedWriter

/* See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* Esri Inc. licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License.  You may obtain a copy of the License at
*
*     http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.esri.gpt.control.georss;

import com.esri.gpt.catalog.discovery.rest.RestQuery;
import com.esri.gpt.catalog.search.*;
import com.esri.gpt.control.georss.IFeedRecords.FieldMeta;
import com.esri.gpt.control.georss.RestQueryServlet.ResponseFormat;
import com.esri.gpt.framework.context.ApplicationConfiguration;
import com.esri.gpt.framework.context.ApplicationContext;
import com.esri.gpt.framework.context.RequestContext;
import com.esri.gpt.framework.context.UrnMap;
import com.esri.gpt.framework.geometry.Envelope;
import com.esri.gpt.framework.isodate.IsoDateFormat;
import com.esri.gpt.framework.jsf.MessageBroker;
import com.esri.gpt.framework.util.Val;
import java.io.IOException;
import java.io.PrintWriter;
import java.lang.reflect.Constructor;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Comparator;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
import java.util.TreeSet;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.regex.Pattern;
import java.util.regex.PatternSyntaxException;
import javax.servlet.http.HttpServletRequest;
import org.json.JSONException;

/**
* JSON feed writer.
* Writes response in JSON (or pretty JSON) format.
* <p/>
* Uses <i>json.writer.className</i> parameter from <b>gpt.xml</b> to create an instance.
* Creates default instance if parameter is empty.
* <p/>
* Default implementation uses <i>json.predicate.banned</i> parameter from <b>gpt.xml</b>,
* which is a regular expression used to stop printing certain fields. Note
* that fields beginning with "index.sys.xml" are not printed by default; the
* only way to have it printed is to specify them explicitely in <i>outFields</i>
* request parameter.
* @see JsonSearchEngine
*/
public class ExtJsonFeedWriter implements FeedWriter {

  /**
   * Logger.
   */
  protected static final Logger LOG = Logger.getLogger(ExtJsonFeedWriter.class.getCanonicalName());
  /**
   * tab size
   */
  private final static int TAB_SIZE = 2;
  /**
   * ISO date format
   */
  protected final static IsoDateFormat DF = new IsoDateFormat();
  /**
   * parameter map
   */
  protected Map<String,String[]> parameterMap;
  /**
   * print writer
   */
  private PrintWriter writer;
  /**
   * original query
   */
  protected RestQuery query;
  /**
   * flag indicating if is this a pretty formated JSON
   */
  private boolean pretty;
  /**
   * predicates
   */
  protected Pattern predicateBanned;
  /**
   * indentation level
   */
  private int level = 0;
  /**
   * message broker
   */
  protected MessageBroker messageBroker;

  /**
   * Creates instance of the feed writer.
   *
   * @param parameterMap parameter map
   * @param context request context
   * @param writer writer
   * @param query query
   * @param pretty <code>true</code> for 'pretty' JSON output
   * @return instance of {@link ExtJsonFeedWriter}
   */
  public static ExtJsonFeedWriter createInstance(Map<String,String[]> parameterMap, RequestContext context, PrintWriter writer, RestQuery query, Boolean pretty) {
    String className = getConfigParam("json.writer.className");
    if (className.isEmpty()) {
      return new ExtJsonFeedWriter(parameterMap, context, writer, query, pretty);
    } else {
      try {
        //TODO this code throws exception
        Class writerClass = Class.forName(className);
        Constructor constructor = writerClass.getConstructor(new Class[]{Map.class, RequestContext.class, PrintWriter.class, RestQuery.class, Boolean.class});
        return (ExtJsonFeedWriter) constructor.newInstance(parameterMap,context, writer, query, pretty);
        //return new DcatJsonFeedWriter(request, context, writer, query, pretty);
      } catch (Exception ex) {
        LOG.log(Level.INFO, "Error creating JSON feed writer class: " + className + ". Using default writer instead.", ex);
        return new ExtJsonFeedWriter(parameterMap, context, writer, query, pretty);
      }
    }
  }

  /**
   * Creates instance of the feed writer.
   *
   * @param request HTTP servlet request
   * @param context request context
   * @param writer writer
   * @param query query
   * @param pretty <code>true</code> for 'pretty' JSON output
   * @return instance of {@link ExtJsonFeedWriter}
   */
  public static ExtJsonFeedWriter createInstance(HttpServletRequest request, RequestContext context, PrintWriter writer, RestQuery query, Boolean pretty) {
    return createInstance(request.getParameterMap(), context, writer, query, pretty);
  }

  /**
   * Sets message broker
   *
   * @param messageBroker the messageBroker to set
   */
  public void setMessageBroker(MessageBroker messageBroker) {
    this.messageBroker = messageBroker;
  }

  /**
   * Gets message broker
   *
   * @return the messageBroker
   */
  public MessageBroker getMessageBroker() {
    return messageBroker;
  }
 
  @Override
  public void write(IFeedRecords records) {
    if (Val.chkBool(getRequestParam("returnCountOnly"),false)) {
      writeCountOnly(records.getOpenSearchProperties().getNumberOfHits());
      return;
    }
   
    if (Val.chkBool(getRequestParam("returnIdsOnly"),false)) {
      writeIdsOnly(records);
      return;
    }
           
    String sTitle = messageBroker.retrieveMessage("catalog.rest.title");
    String sDescription = messageBroker.retrieveMessage("catalog.rest.description");
    String sCopyright = messageBroker.retrieveMessage("catalog.rest.copyright");
    String sGenerator = messageBroker.retrieveMessage("catalog.rest.generator");

    if (sTitle.startsWith("???")) {
      sTitle = "";
    }
    if (sDescription.startsWith("???")) {
      sDescription = "";
    }
    if (sCopyright.startsWith("???")) {
      sCopyright = "";
    }
    if (sGenerator.startsWith("???")) {
      sGenerator = "";
    }

    println("{");
    levelUp();

    printArg("title", sTitle, true);
    printArg("description", sDescription, true);
    printArg("copyright", sCopyright, true);
    printArg("updated", DF.format(new Date()), true);
    printArg("type", "FeatureCollection", true);
    if (query != null) {
      printArg("provider", query.getRssProviderUrl(), true);
      printArg("source", query.getRssSourceUrl(), true);
      if (!query.getRepositoryId().isEmpty()) {
        printArg("repositoryId", query.getRepositoryId(), true);
      }
    }
    OpenSearchProperties osProps = records.getOpenSearchProperties();
    if (osProps != null) {
      Long totalResults = new Long(osProps.getNumberOfHits());
      Long startIndex = new Long(osProps.getStartRecord());
      Long itemsPerPage = new Long(osProps.getRecordsPerPage());
      if (query != null) {
        if (startIndex + itemsPerPage - 1 < totalResults) {
          printArg("more", query.getMoreUrl(), true);
        }
      }
      printArg("totalResults", totalResults, true);
      printArg("startIndex", startIndex, true);
      printArg("itemsPerPage", itemsPerPage, true);
    }

    printArg("displayFieldName", sTitle, true);
    println("\"fieldAliases\": {");
    levelUp();
    List<FieldMeta> fml = new ArrayList();
    for (FieldMeta fm: records.getMetaData()) {
      if (checkAttr(fm.getName())) {
        fml.add(fm);
      }
    }
    for (int i = 0; i < fml.size(); i++) {
      FieldMeta f = fml.get(i);
      printArg(f.getName(), f.getAlias(), i < fml.size() - 1);
    }
    levelDown();
    println("},");
    printArg("geometryType", "esriGeometryPolygon", true);
    println("\"spatialReference\": { \"wkid\": " +getOutputSpatialReference()+ " },");
    println("\"fields\": [");
    levelUp();
    for (int i = 0; i < fml.size(); i++) {
      FieldMeta f = fml.get(i);
      printField(f, i < fml.size() - 1);
    }
    levelDown();
    println("],");

    printRecords(records, true);
    printAPI(false);
    levelDown();
    println("}");
  }

  /**
   * Creates instance of the feed.
   *
   * @param request HTTP request
   * @param context request context
   * @param writer writer to write feed
   * @param query query
   * @param pretty <code>true</code> to print pretty response
   */
  public ExtJsonFeedWriter(HttpServletRequest request, RequestContext context, PrintWriter writer, RestQuery query, Boolean pretty) {
    this(request.getParameterMap(), context, writer, query, pretty);
  }
 
  /**
   * Creates instance of the feed.
   *
   * @param parameterMap parameter map
   * @param context request context
   * @param writer writer to write feed
   * @param query query
   * @param pretty <code>true</code> to print pretty response
   */
  public ExtJsonFeedWriter(Map<String,String[]> parameterMap, RequestContext context, PrintWriter writer, RestQuery query, Boolean pretty) {
    this.parameterMap = parameterMap;
    this.writer = writer;
    this.query = query;
    this.pretty = pretty;

    String sPredicateBanned = getConfigParam("json.predicate.banned");

    if (!sPredicateBanned.isEmpty()) {
      try {
        this.predicateBanned = Pattern.compile(sPredicateBanned);
      } catch (PatternSyntaxException ex) {
        Logger.getLogger(ExtJsonFeedWriter.class.getCanonicalName()).log(Level.INFO, "Error compiling predicate: " + sPredicateBanned, ex);
      }
    }
  }

  /**
   * Writes number of matching records only.
   * @param numberOfHits
   */
  protected void writeCountOnly(int numberOfHits) {
    println("{");
    levelUp();
    printArg("count", numberOfHits, false);
    levelDown();
    println("}");
  }
 
  /**
   * Writes records ids only.
   * @param records list of records
   */
  protected void writeIdsOnly(List<IFeedRecord> records) {
    println("{");
    levelUp();
    printArg("objectIdFieldName", "UUID", true);
    println("\"objectIds\": [");
    levelUp();
   
    for (int i=0; i<records.size(); i++) {
      IFeedRecord r = records.get(i);
      String uuid = r.getUuid();
      println("\""+uuid+"\""+(i<records.size()-1? ",": ""));
    }
   
    levelDown();
    println("]");
    levelDown();
    println("}");
  }

  /**
   * Prints a field.
   *
   * @param f field
   * @param more more fields
   */
  protected void printField(FieldMeta f, boolean more) {
    println("{");
    levelUp();
    printArg("name", f.getName(), true);
    printArg("type", f.getType(), true);
    printArg("alias", f.getAlias(), f.getLength() != null);
    if (f.getLength() != null) {
      printArg("length", f.getLength(), false);
    }
    levelDown();
    println("}" + (more ? "," : ""));
  }

  /**
   * Prints all records.
   *
   * @param records records to print
   * @param more <code>true</code> if more info will be printed after that
   * section
   */
  protected void printRecords(IFeedRecords records, boolean more) {
    try {
      List<Envelope> envelopes = new ArrayList<Envelope>();
      for (IFeedRecord r : records) {
        envelopes.add(r.getEnvelope());
      }
      String outSR = getRequestParam("outSR");
      if (!outSR.isEmpty() && !"4326".equals(outSR)) {
        GeometryService gs = GeometryService.createDefaultInstance();
        envelopes = gs.project(envelopes, outSR);
      }

      println("\"features\"" + sp() + ":" + sp() + "[");
      levelUp();

      for (int i = 0; i < records.size(); i++) {
        printRecord(records.get(i), envelopes.get(i), i < records.size() - 1);
      }

      levelDown();
      println("]" + (more ? "," : ""));
    } catch (IOException ex) {
      LOG.log(Level.SEVERE, "Error writing records", ex);
    } catch (JSONException ex) {
      LOG.log(Level.SEVERE, "Error writing records", ex);
    }
  }

  /**
   * Prints record.
   *
   * @param r record to print
   * @param env envelope
   * @param more <code>true</code> if more info will be printed after that
   * section
   */
  protected void printRecord(IFeedRecord r, Envelope env, boolean more) {
    println("{");
    levelUp();

    printArg("type", "Feature", true);
    printAttributes("properties", r, true);
    printAttributes("attributes", r, true);
   
    if (!hasRequestParam("returnGeometry") || Val.chkBool(getRequestParam("returnGeometry"), true)) {
      printGeometry(env, true);
    }


    ResourceLinks links = r.getResourceLinks();
    printLinks(links, true);

    printResources(links, false);

    levelDown();
    println("}" + (more ? "," : ""));
  }

  /**
   * Prints attributes.
   *
   * @param name name
   * @param r record
   * @param more <code>true</code> if more info will be printed after that
   * section
   */
  protected void printAttributes(String name, IFeedRecord r, boolean more) {
    println("\"" +name+ "\"" + sp() + ":" + sp() + "{");
    levelUp();

    Map<String, IFeedAttribute> index = r.getData(IFeedRecord.STD_COLLECTION_INDEX);
    List<String> indexKeys = new ArrayList<String>(index.keySet());

    ArrayList<Map.Entry<String, IFeedAttribute>> entries = new ArrayList<Map.Entry<String, IFeedAttribute>>(r.getData(IFeedRecord.STD_COLLECTION_CATALOG).entrySet());
    Collections.sort(entries, new Comparator<Map.Entry<String, IFeedAttribute>>() {
      @Override
      public int compare(Entry<String, IFeedAttribute> o1, Entry<String, IFeedAttribute> o2) {
        return o1.getKey().compareToIgnoreCase(o2.getKey());
      }
    });

    boolean before = false;

    if (checkAttr("objectid")) {
      before = printAttr(before, "objectid", r.getObjectId());
    }
    if (checkAttr("title")) {
      before = printAttr(before, "title", r.getTitle());
    }
    if (checkAttr("id")) {
      before = printAttr(before, "id", r.getUuid());
    }
    if (checkAttr("fileIdentifier") && !r.getFileIdentifier().isEmpty()) {
      before = printAttr(before, "fileIdentifier", r.getFileIdentifier());
    }
    if (checkAttr("updated") && r.getModfiedDate() instanceof Date) {
      before = printAttr(before, "updated", DF.format(r.getModfiedDate()));
    }
    if (checkAttr("contentType") && !r.getContentType().isEmpty()) {
      before = printAttr(before, "contentType", UrnMap.URN_ESRI_GPT + ":contentType:" + r.getContentType());
    }
    if (checkAttr("summary")) {
      before = printAttr(before, "summary", r.getAbstract());
    }

    for (int i = 0; i < indexKeys.size(); i++) {
      String indexKey = indexKeys.get(i);
      IFeedAttribute indexValue = index.get(indexKey);

      String attrName = IFeedRecord.STD_COLLECTION_INDEX+"." + indexKey;
      if (checkAttr(attrName)) {
        if (before) {
          print(false, ",");
          print(false, "\r\n");
        }
        print(before, "\"" + attrName + "\"" + sp() + ":" + sp() + indexValue);
        before = true;
      }
    }

    for (int i = 0; i < entries.size(); i++) {
      Entry<String, IFeedAttribute> e = entries.get(i);

      String attrName = IFeedRecord.STD_COLLECTION_CATALOG+"." + e.getKey();
      if (checkAttr(attrName)) {
        if (before) {
          print(false, ",");
          print(false, "\r\n");
        }
        print(before, "\"" + attrName + "\"" + sp() + ":" + sp() + e.getValue());
        before = true;
      }
    }

    print(false, "\r\n");

    levelDown();
    println("}" + (more ? "," : ""));
  }

  /**
   * Prints geometry.
   *
   * @param env geometry
   * @param more flag to indicate if there will be more arguments
   */
  protected void printGeometry(Envelope env, boolean more) {
    println("\"geometry\"" + sp() + ":" + sp() + "{");
    levelUp();
    printArg("type", "Polygon", true);
    printPolygonShape("coordinates",env, true);
    printPolygonShape("rings",env, false);
    levelDown();
    println("}" + (more ? "," : ""));
  }

  /**
   * Prints a polygon.
   *
   * @param env
   */
  protected void printPolygonShape(String name, Envelope env, boolean more) {
  //printArg("type", "Polygon", true);
    println("\"" +name+ "\"" + sp() + ":" + sp() + "[");
    printPolygon(env);
    println("]" + (more ? "," : ""));
  //  println("],");
  //  println("\"spatialReference\":{\"wkid\":" + Val.chkStr(env.getWkid(), getOutputSpatialReference()) + "  }");
  }

  /**
   * Prints polygon.
   *
   * @param env polygon to print
   */
  protected void printPolygon(Envelope env) {
    levelUp();
    println("[");
    levelUp();
    println(
            coord(env.getMinX(), env.getMinY()) + "," + sp()
            + coord(env.getMinX(), env.getMaxY()) + "," + sp()
            + coord(env.getMaxX(), env.getMaxY()) + "," + sp()
            + coord(env.getMaxX(), env.getMinY()) + "," + sp()
            + coord(env.getMinX(), env.getMinY()));
    levelDown();
    println("]");
    levelDown();
  }

  /**
   * Prints all links.
   *
   * @param links collection of resource links
   * @param more flag to indicate if there will be more arguments
   */
  protected void printLinks(ResourceLinks links, boolean more) {
    RequestContext rc = RequestContext.extract(null);
    ResourceIdentifier ri = ResourceIdentifier.newIdentifier(rc);

    println("\"links\"" + sp() + ":" + sp() + "[");
    levelUp();

    ArrayList<ResourceLink> allLinks = new ArrayList<ResourceLink>();
    for (int j = 0; j < links.size(); j++) {
      ResourceLink rl = links.get(j);
      if (!rl.getTag().equals(ResourceLink.TAG_CONTENTTYPE) && !rl.getTag().equals(ResourceLink.TAG_THUMBNAIL)) {
        allLinks.add(links.get(j));
      }
    }

    for (int i = 0; i < allLinks.size(); i++) {
      printLink(ri, allLinks.get(i), i < allLinks.size() - 1);
    }

    levelDown();
    println("]" + (more ? "," : ""));
  }

  /**
   * Prints all resources.
   *
   * @param links collection of resource links
   * @param more flag to indicate if there will be more arguments
   */
  protected void printResources(ResourceLinks links, boolean more) {
    RequestContext rc = RequestContext.extract(null);
    ResourceIdentifier ri = ResourceIdentifier.newIdentifier(rc);

    println("\"resources\"" + sp() + ":" + sp() + "[");
    levelUp();

    ResourceLink thumbnail = links.getThumbnail();
    ResourceLink icon = links.getIcon();

    if (thumbnail != null) {
      printLink(ri, thumbnail, icon != null);
    }
    if (icon != null) {
      printLink(ri, icon, false);
    }

    levelDown();
    println("]" + (more ? "," : ""));
  }

  /**
   * Prints a link.
   *
   * @param ri resource identifier
   * @param link resource link
   * @param more flag to indicate if there will be more arguments
   */
  protected final void printLink(ResourceIdentifier ri, ResourceLink link, boolean more) {
    if (!link.getTag().isEmpty() && !link.getUrl().isEmpty()) {
      String tag = link.getTag().equals(ResourceLink.TAG_CONTENTTYPE) ? "icon" : link.getTag();
      printLink(link.getUrl(), tag, link.getLabel(), guessServiceUrn(ri, link), more);
    }
  }

  /**
   * Prints link.
   *
   * @param url url
   * @param tag tag
   * @param label label
   * @param urn classified as urn
   * @param more flag to indicate if there will be more arguments
   */
  protected void printLink(String url, String tag, String label, String urn, boolean more) {
    println("{");
    levelUp();
    printArg("href", url, true);
    printArg("hrefType", UrnMap.URN_ESRI_GPT + ":hrefType:" + tag, true);
    printArg("label", label, true);
    printArg("type", tag, !urn.isEmpty());
    if (!urn.isEmpty()) {
      printArg("classifiedAs", urn, false);
    }
    levelDown();
    println("}" + (more ? "," : ""));
  }

  /**
   * Prints bottom links.
   *
   * @param more more links
   */
  protected void printAPI(boolean more) {
    //String [] alts  = new String[]{"georss","atom","html","htmlfragment","json","xjson","kml","csv"};
    ArrayList<ResponseFormat> alts = new ArrayList<ResponseFormat>();
    for (ResponseFormat f : ResponseFormat.values()) {
      if (f.isApi()) {
        alts.add(f);
      }
    }
    println("\"api\": [");
    if (query != null) {
      levelUp();
      for (int i = 0; i < alts.size(); i++) {
        ResponseFormat alt = alts.get(i);
        String label = alt.name().toUpperCase();
        if (alt == ResponseFormat.htmlfragment) {
          label = "FRAGMENT";
        }
        if (alt == ResponseFormat.pjson) {
          label = "JSON";
        }
        if (alt == ResponseFormat.xjson) {
          label = "JSON (Extended)";
        }
        String url = query.getRssSourceUrl().replaceAll(
                "f=" + ResponseFormat.pjson + "|f=" + ResponseFormat.json + "|f=" + ResponseFormat.xjson,
                "f=" + (alt == ResponseFormat.json ? ResponseFormat.pjson : alt));
        printLink(url, alt.name(), label, "", i < alts.size() - 1);
      }
      levelDown();
    }
    println("]" + (more ? "," : ""));
  }

  /**
   * Guesses URN of resource link type.
   *
   * @param ri instance of resource identifier
   * @param link resource link
   * @return URN of resource link type
   */
  protected String guessServiceUrn(ResourceIdentifier ri, ResourceLink link) {
    if (link.getTag().equals(ResourceLink.TAG_OPEN)) {
      return ri.guessServiceUrnFromUrl(link.getUrl());
    }
    return "";
  }

  /**
   * Prints argument.
   *
   * @param argName argument name
   * @param argVal argument value
   * @param more flag to indicate if there will be more arguments
   */
  protected final void printArg(String argName, String argVal, boolean more) {
    argName = Val.chkStr(argName);
    argVal = Val.chkStr(argVal);
    if (argName.length() > 0) {
      println("\"" + Val.escapeStrForJson(argName) + "\"" + sp() + ":" + sp() + "\"" + Val.escapeStrForJson(argVal) + "\"" + (more ? "," : ""));
    }
  }

  /**
   * Prints argument.
   *
   * @param argName argument name
   * @param argVal argument value
   * @param more flag to indicate if there will be more arguments
   */
  protected final void printArg(String argName, Number argVal, boolean more) {
    argName = Val.chkStr(argName);
    if (argName.length() > 0) {
      println("\"" + Val.escapeStrForJson(argName) + "\"" + sp() + ":" + sp() + argVal + (more ? "," : ""));
    }
  }

  /**
   * Prints attribute.
   *
   * @param before <ocde>true</code> if anything has been printed before
   * @param argName argument name
   * @param argVal argument value
   * @return <code>true</code> if anything has been printed
   */
  protected final boolean printAttr(boolean before, String argName, String argVal) {
    argName = Val.chkStr(argName);
    argVal = Val.chkStr(argVal);
    if (checkAttr(argName) && argName.length() > 0) {
      if (before) {
        print(false, ",");
        print(false, "\r\n");
      }
      print(true, "\"" + Val.escapeStrForJson(argName) + "\"" + sp() + ":" + sp() + "\"" + Val.escapeStrForJson(argVal) + "\"");
      before = true;
    }
    return before;
  }

  /**
   * Prints attribute.
   *
   * @param before <ocde>true</code> if anything has been printed before
   * @param argName argument name
   * @param argVal argument value
   * @return <code>true</code> if anything has been printed
   */
  protected final boolean printAttr(boolean before, String argName, long argVal) {
    argName = Val.chkStr(argName);
    if (checkAttr(argName) && argName.length() > 0) {
      if (before) {
        print(false, ",");
        print(false, "\r\n");
      }
      print(true, "\"" + Val.escapeStrForJson(argName) + "\"" + sp() + ":" + sp() + argVal);
      before = true;
    }
    return before;
  }

  /**
   * Makes coordinates.
   *
   * @param x x coordinate
   * @param y y coordinate
   * @return coordinate in JSON format
   */
  protected String coord(double x, double y) {
    return "[" + String.format("%f",x) + "," + String.format("%f",y) + "]";
  }

  /**
   * Checks if attribute of a given name can be printed.
   *
   * @param attrName attribute name
   * @return <code>true</code> if attribute can be printed
   */
  protected boolean checkAttr(String attrName) {
    Set<String> outFieldsSet = buildOutFieldsSet();
   
    // check if any xml is allowed; by default no xml is allowed, only if specified
    // in outFields
    String xmlField = IFeedRecord.STD_COLLECTION_INDEX+"."+"sys.xml";
    if (attrName.startsWith(xmlField) && (outFieldsSet==null || !outFieldsSet.contains(attrName))) {
      return false;
    }
   
    // must pass banned predicate; 'banned' is a regular expression which competly
    // hides a field from reading - even specifying it in outFields will not let it pass
    if (predicateBanned != null && predicateBanned.matcher(attrName).matches()) {
      return false;
    }
   
    // check if user requested specified fields through oufFields; if specified
    // and the current attribute is not on that list, don't print it
    if (outFieldsSet!=null && !outFieldsSet.contains(attrName)) {
      return false;
    }
   
   
    return true;
  }
 
  /**
   * Builds collection of names of fields for output.
   * @return set of fields names.
   */
  protected Set<String> buildOutFieldsSet() {
    Set<String> outFieldsSet = null;
    String outFields = getRequestParam("outFields");
    if (!outFields.isEmpty() && !outFields.equals("*")) {
      outFieldsSet = new TreeSet<String>(Arrays.asList(outFields.split(",")));
    }
    return outFieldsSet;
  }

  /**
   * Gets configuration parameter.
   *
   * @param paramName parameter name
   * @return parameter value
   */
  protected static String getConfigParam(String paramName) {
    ApplicationContext appCtx = ApplicationContext.getInstance();
    ApplicationConfiguration appCfg = appCtx.getConfiguration();
    return Val.chkStr(appCfg.getCatalogConfiguration().getParameters().getValue(paramName));
  }

  /**
   * Gets request parameter.
   *
   * @param paramName parameter name
   * @return request parameter
   */
  protected String getRequestParam(String paramName) {
    String[] paramValues = parameterMap.get(paramName);
    if (paramValues!=null) {
      for (String param: parameterMap.get(paramName)) {
        param = Val.chkStr(param);
        if (!param.isEmpty()) {
          return param;
        }
      }
    }
    return "";
  }
 
  /**
   * Checks if parameter has even been supplied.
   * @param paramName parameter name
   * @return <code>true</code> if parameter is present (even an empty string)
   */
  protected boolean hasRequestParam(String paramName) {
    String[] paramValues = parameterMap.get(paramName);
    return paramValues!=null && paramValues.length>0;
  }

  /**
   * Gets output spatial reference.
   * @return output spatial reference. Default: <b>4326</b>.
   */
  protected String getOutputSpatialReference() {
      String outSR = getRequestParam("outSR");
      if (!outSR.isEmpty()) {
        return outSR;
      }
      return "4326";
  }
 
  /**
   * Increases level of indentation.
   */
  protected final void levelUp() {
    level++;
  }

  /**
   * Decreases level of indentation.
   */
  protected final void levelDown() {
    level--;
  }

  /**
   * Prints a single line. Depending on the 'pretty' flag, line is indented or
   * not.
   *
   * @param text text to print
   */
  protected final void println(String text) {
    if (pretty) {
      printTab();
      writer.println(text);
    } else {
      writer.print(text);
    }
  }

  /**
   * Prints a single line without ending it with a new line.
   *
   * @param indent <code>true</code> to indent the line
   * @param text text to print
   */
  protected final void print(boolean indent, String text) {
    if (pretty) {
      if (indent) {
        printTab();
      }
      writer.print(text);
    } else {
      writer.print(text);
    }
  }

  /**
   * Prints tabulator. Tabulator width depends on the indentation level.
   */
  protected final void printTab() {
    for (int i = 0; i < level * TAB_SIZE; i++) {
      writer.print(" ");
    }
  }

  /**
   * Creates a single space. Depending on the 'pretty' flag, it's either a space
   * or no space at all.
   *
   * @return single space
   */
  protected final String sp() {
    return pretty ? " " : "";
  }
}
TOP

Related Classes of com.esri.gpt.control.georss.ExtJsonFeedWriter

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.