/*******************************************************************************
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF 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.
 *******************************************************************************/
options {
  ERROR_REPORTING = true;
  STATIC = false;
//  DEBUG_PARSER = true;
//  DEBUG_LOOKAHEAD = true;
//  DEBUG_TOKEN_MANAGER = true;
  LOOKAHEAD = 1;
//  CHOICE_AMBIGUITY_CHECK = 3;
//  OTHER_AMBIGUITY_CHECK = 3;
}

PARSER_BEGIN(JSON)

package org.ofbiz.base.json;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;

import javolution.util.FastMap;

import org.ofbiz.base.util.UtilIO;

public class JSON {
    private boolean allowResolve;

    public JSON(String fileName) {
        this(System.in);
        try { ReInit(new FileInputStream(new File(fileName))); }
        catch(Exception e) { e.printStackTrace(); }
//        allowed[TEXT] = 1;
//        allowed[FIRST_COLUMN_TEXT] = 1;
    }

    public JSON allowResolve(boolean allowResolve) {
        this.allowResolve = allowResolve;
    token_source.SwitchTo(allowResolve ? RESOLVE : DEFAULT);
    return this;
    }
}

PARSER_END(JSON)
TOKEN_MGR_DECLS: {
    protected LinkedList<Integer> stateStack = new LinkedList<Integer>();
    protected StringBuilder statePrefix = new StringBuilder();

    protected void pushState(int state) {
        //System.err.println(statePrefix + "push: " + lexStateNames[curLexState] + " -> " + lexStateNames[state]);
        stateStack.add(curLexState);
        statePrefix.append(' ');
        SwitchTo(state);
    }

    protected void popState() {
        int oldState = stateStack.removeLast();
        statePrefix.setLength(statePrefix.length() - 1);
        //System.err.println(statePrefix + "pop: " + lexStateNames[curLexState] + " -> " + lexStateNames[oldState]);
        SwitchTo(oldState);
    }
}
<DEFAULT,RESOLVE>
TOKEN:
{
  <OBJECT_BEGIN: "{">
| <OBJECT_END: "}">
| <ARRAY_BEGIN: "[">
| <ARRAY_END: "]">
| <ITEM_SEP: ",">
| <KEY_SEP: ":">
| <TRUE: "true">
| <FALSE: "false">
| <NULL: "null">
| <WHOLE_NUMBER:
    <NUMBER_PREFIX>
  >
| <FLOAT_NUMBER:
    <NUMBER_PREFIX>
    ("." (["0"-"9"])*)?
    (
      ["e", "E"]
      (["+", "-"])?
      (["0"-"9"])+
    )?
  >
| <#NUMBER_PREFIX:
    (["-"])?
    (
      "0"
    | ["1"-"9"] (["0"-"9"])*
    )
  >
}

<DEFAULT,RESOLVE,IN_RESOLVE_VALUE>
TOKEN:
{
  <STRING_START: "\""> { pushState(IN_STRING); }
}

<IN_RESOLVE_VALUE>
TOKEN:
{
  <CLOSE_PAREN: ")"> { popState(); }
}

<RESOLVE>
TOKEN:
{
  <RESOLVE_BEGIN: "resolve("> { pushState(IN_RESOLVE_VALUE); }
}

<IN_STRING>
TOKEN:
{
  <CHARACTER: (~["\"","\\","\u0000"-"\u001f"])+>
| <STRING_END: "\""> { popState(); }
| <CONTROL_CHAR: "\\" ["\"", "\\", "/", "b","f","n","r","t"]>
| <UNICODE: "\\u"
    ["a"-"f", "A"-"F", "0"-"9"]
    ["a"-"f", "A"-"F", "0"-"9"]
    ["a"-"f", "A"-"F", "0"-"9"]
    ["a"-"f", "A"-"F", "0"-"9"]
  >
}

<DEFAULT,RESOLVE>
SKIP:
{
  <WHITESPACE: [" ", "\r", "\n", "\t"]>
}

<DEFAULT,RESOLVE>
MORE:
{
  <COMMENT_START: "/*"> { if (curLexState != IN_COMMENT) pushState(IN_COMMENT); }
}

<IN_COMMENT>
MORE:
{
  <(~[])>
}

<IN_COMMENT>
MORE:
{
  <COMMENT_END: "*/"> { popState(); }
}

Object JSONValue():
{ Object value; }
{
  value=JSONItem()
  <EOF>
  { return value; }
}

Object JSONItem():
{ Object value; }
{
  (
    value=JSONString()
  | value=JSONLong()
  | value=JSONFloat()
  | value=JSONObject()
  | value=JSONArray()
  | value=True()
  | value=False()
  | value=Null()
  | value=JSONResolve()
  )
  { return value; }
}

Object JSONResolve():
{
  String name, value;
}
{
  <RESOLVE_BEGIN>
  value=JSONString()
  <CLOSE_PAREN>
  {
    try {
      return UtilIO.readObject(value.toCharArray());
    } catch (ClassNotFoundException e) {
      throw generateParseException();
    } catch (IOException e) {
      throw generateParseException();
    }
  }
}
String JSONString():
{
  StringBuilder sb = new StringBuilder();
}
{
  <STRING_START> (
    <CHARACTER> { sb.append(getToken(0).image); }
  | <CONTROL_CHAR> {
    switch (getToken(0).image.charAt(1)) {
      case '"': sb.append('"'); break;
      case '\\': sb.append('\\'); break;
      case '/': sb.append('/'); break;
      case 'b': sb.append('\b'); break;
      case 'f': sb.append('\f'); break;
      case 'n': sb.append('\n'); break;
      case 'r': sb.append('\r'); break;
      case 't': sb.append('\t'); break;
    }
  }
  | <UNICODE> {
    int v = Integer.parseInt(getToken(0).image.substring(2), 16);
    sb.append((char) v);
  }
  )*
  <STRING_END>
  { return sb.toString(); }
}

Long JSONLong():
{}
{
  try {
    <WHOLE_NUMBER> { return new Long(getToken(0).image); }
  } catch (NumberFormatException e) {
    throw generateParseException();
  }
}

Double JSONFloat():
{}
{
  try {
    <FLOAT_NUMBER> { return new Double(getToken(0).image); }
  } catch (NumberFormatException e) {
    throw generateParseException();
  }
}

Map<String, Object> JSONObject():
{
  Map<String, Object> map = FastMap.newInstance();
}
{
  <OBJECT_BEGIN>
  (JSONObjectEntry(map))? (<ITEM_SEP> (JSONObjectEntry(map))?)*
  <OBJECT_END>
  { return map; }
}

void JSONObjectEntry(Map<String, Object> map):
{
  String key;
  Object value;
}
{
  key=JSONString() <KEY_SEP> value=JSONItem()
  { map.put(key, value); }
}

List<Object> JSONArray():
{
  ArrayList<Object> list = new ArrayList<Object>();
  Object value;
}
{
  <ARRAY_BEGIN>
  (<ITEM_SEP>)*
  (
    value=JSONItem() { list.add(value); }
    (
      <ITEM_SEP>
      (value=JSONItem() { list.add(value); })?
    )*
  )?
  <ARRAY_END>
  { return list; }
}

Boolean True():
{}
{
  <TRUE> { return Boolean.TRUE; }
}

Boolean False():
{}
{
  <FALSE> { return Boolean.FALSE; }
}

Object Null():
{}
{
  <NULL> { return null; }
}
