/*
 * 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.
 */
package org.apache.drill.exec.compile;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.io.Reader;
import java.io.StringReader;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.HashMap;
import java.util.Map;

import javax.tools.SimpleJavaFileObject;

import com.google.common.collect.Maps;

/* package */
final class DrillJavaFileObject extends SimpleJavaFileObject {
  private final String sourceCode;

  private final ByteArrayOutputStream outputStream;

  private Map<String, DrillJavaFileObject> outputFiles;

  private final String className;

  public DrillJavaFileObject(final String className, final String sourceCode) {
    super(makeURI(className), Kind.SOURCE);
    this.className = className;
    this.sourceCode = sourceCode;
    this.outputStream = null;
  }

  private DrillJavaFileObject(final String name, final Kind kind) {
    super(makeURI(name), kind);
    this.className = name;
    this.outputStream = new ByteArrayOutputStream();
    this.sourceCode = null;
  }

  public boolean isCompiled() {
    return (outputFiles != null);
  }

  public byte[][] getByteCode() {
    if (!isCompiled()) {
      return null;
    } else {
      int index = 0;
      byte[][] byteCode = new byte[outputFiles.size()][];
      for(DrillJavaFileObject outputFile : outputFiles.values()) {
        byteCode[index++] = outputFile.outputStream.toByteArray();
      }
      return byteCode;
    }
  }

  /**
   * Return the byte codes for the main class and any nested
   * classes.
   *
   * @return map of fully-qualified class names to byte codes
   * for the class
   */

  public Map<String,byte[]> getClassByteCodes() {
    Map<String,byte[]> results = new HashMap<>();
    for(DrillJavaFileObject outputFile : outputFiles.values()) {
      results.put(outputFile.className, outputFile.outputStream.toByteArray());
    }
    return results;
  }

  public DrillJavaFileObject addOutputJavaFile(String className) {
    if (outputFiles == null) {
      outputFiles = Maps.newLinkedHashMap();
    }
    DrillJavaFileObject outputFile = new DrillJavaFileObject(className, Kind.CLASS);
    outputFiles.put(className, outputFile);
    return outputFile;
  }

  @Override
  public Reader openReader(final boolean ignoreEncodingErrors) throws IOException {
    return new StringReader(sourceCode);
  }

  @Override
  public CharSequence getCharContent(final boolean ignoreEncodingErrors) throws IOException {
    if (sourceCode == null) {
      throw new UnsupportedOperationException("This instance of DrillJavaFileObject is not an input object.");
    }
    return sourceCode;
  }

  @Override
  public OutputStream openOutputStream() {
    if (outputStream == null) {
      throw new UnsupportedOperationException("This instance of DrillJavaFileObject is not an output object.");
    }
    return outputStream;
  }

  private static URI makeURI(final String canonicalClassName) {
    final int dotPos = canonicalClassName.lastIndexOf('.');
    final String simpleClassName = dotPos == -1 ? canonicalClassName : canonicalClassName.substring(dotPos + 1);
    try {
      return new URI(simpleClassName + Kind.SOURCE.extension);
    } catch (URISyntaxException e) {
      throw new RuntimeException(e);
    }
  }

}
