import errno
import fnmatch
import json
import os
import re
import subprocess
import sys


MODULE_XML_START = """<?xml version="1.0" encoding="UTF-8"?>
<module type="%(type)s" version="4">"""

MODULE_XML_END = """
</module>
"""

ANDROID_FACET = """
  <component name="FacetManager">
    <facet type="android" name="Android">
      <configuration>
        <option name="GEN_FOLDER_RELATIVE_PATH_APT" value="%(module_gen_path)s" />
        <option name="GEN_FOLDER_RELATIVE_PATH_AIDL" value="%(module_gen_path)s" />
        <option name="MANIFEST_FILE_RELATIVE_PATH" value="%(android_manifest)s" />
        <option name="RES_FOLDER_RELATIVE_PATH" value="%(res)s" />
        <option name="ASSETS_FOLDER_RELATIVE_PATH" value="/assets" />
        <option name="LIBS_FOLDER_RELATIVE_PATH" value="%(libs_path)s" />
        <option name="USE_CUSTOM_APK_RESOURCE_FOLDER" value="false" />
        <option name="CUSTOM_APK_RESOURCE_FOLDER" value="" />
        <option name="USE_CUSTOM_COMPILER_MANIFEST" value="false" />
        <option name="CUSTOM_COMPILER_MANIFEST" value="" />
        <option name="APK_PATH" value="" />
        <option name="LIBRARY_PROJECT" value="%(is_android_library_project)s" />
        <option name="RUN_PROCESS_RESOURCES_MAVEN_TASK" value="true" />
        <option name="GENERATE_UNSIGNED_APK" value="false" />
        <option name="CUSTOM_DEBUG_KEYSTORE_PATH" value="%(keystore)s" />
        <option name="PACK_TEST_CODE" value="false" />
        <option name="RUN_PROGUARD" value="%(run_proguard)s" />
        <option name="PROGUARD_CFG_PATH" value="%(proguard_config)s" />
        <resOverlayFolders />
        <includeSystemProguardFile>false</includeSystemProguardFile>
        <includeAssetsFromLibraries>true</includeAssetsFromLibraries>
        <additionalNativeLibs />
      </configuration>
    </facet>
  </component>"""

ALL_MODULES_XML_START = """<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
  <component name="ProjectModuleManager">
    <modules>"""

ALL_MODULES_XML_END = """
    </modules>
  </component>
</project>
"""

LIBRARY_XML_START = """<component name="libraryTable">
  <library name="%(name)s">
    <CLASSES>
      <root url="jar://$PROJECT_DIR$/%(binary_jar)s!/" />
    </CLASSES>"""

LIBRARY_XML_WITH_JAVADOC = """
    <JAVADOC>
      <root url="%(javadoc_url)s" />
    </JAVADOC>"""

LIBRARY_XML_NO_JAVADOC = """
    <JAVADOC />"""

LIBRARY_XML_WITH_SOURCES = """
    <SOURCES>
      <root url="jar://$PROJECT_DIR$/%(source_jar)s!/" />
    </SOURCES>"""

LIBRARY_XML_NO_SOURCES = """
    <SOURCES />"""

LIBRARY_XML_END = """
  </library>
</component>
"""

RUN_CONFIG_XML_START = """<component name="ProjectRunConfigurationManager">"""
RUN_CONFIG_XML_END = "</component>"

REMOTE_RUN_CONFIG_XML = """
  <configuration default="false" name="%(name)s" type="Remote" factoryName="Remote">
    <option name="USE_SOCKET_TRANSPORT" value="true" />
    <option name="SERVER_MODE" value="false" />
    <option name="SHMEM_ADDRESS" value="javadebug" />
    <option name="HOST" value="localhost" />
    <option name="PORT" value="5005" />
    <RunnerSettings RunnerId="Debug">
      <option name="DEBUG_PORT" value="5005" />
      <option name="TRANSPORT" value="0" />
      <option name="LOCAL" value="false" />
    </RunnerSettings>
    <ConfigurationWrapper RunnerId="Debug" />
    <method />
  </configuration>
"""


# Files that were written by this script.
# If `buck project` is working properly, most of the time it will be a no-op
# and no files will need to be written.
MODIFIED_FILES = []

# Files that are part of the project being run.  We will delete all .iml files
# that are not checked in and not in this set.
PROJECT_FILES = set()

def write_modules(modules):
  """Writes one XML file for each module."""
  for module in modules:
    # Build up the XML.
    module_type = 'JAVA_MODULE'
    if 'isIntelliJPlugin' in module and module['isIntelliJPlugin']:
      module_type = 'PLUGIN_MODULE'

    xml = MODULE_XML_START % {
      'type': module_type,
    }

    # Android facet, if appropriate.
    if module.get('hasAndroidFacet') == True:
      if 'keystorePath' in module:
        keystore = 'file://$MODULE_DIR$/%s' % module['keystorePath']
      else:
        keystore = ''

      if 'androidManifest' in module:
        android_manifest = module['androidManifest']
      else:
        android_manifest = '/AndroidManifest.xml'

      is_library_project = module['isAndroidLibraryProject']
      android_params = {
        'android_manifest': android_manifest,
        'res': '/res',
        'is_android_library_project': str(is_library_project).lower(),
        'run_proguard': 'false',
        'module_gen_path': module['moduleGenPath'],
        'proguard_config': '/proguard.cfg',
        'keystore': keystore,
        'libs_path' : '/%s' % module.get('nativeLibs', 'libs'),
      }
      xml += ANDROID_FACET % android_params

    # Source code and libraries component.
    xml += '\n  <component name="NewModuleRootManager" inherit-compiler-output="true">'

    # Empirically, if there are multiple source folders, then the <content> element for the
    # buck-out/android/gen folder should be listed before the other source folders.
    num_source_folders = len(module['sourceFolders'])
    if num_source_folders > 1:
      xml = add_buck_android_source_folder(xml, module)

    # Source folders.
    xml += '\n    <content url="file://$MODULE_DIR$">'
    for source_folder in module['sourceFolders']:
      if 'packagePrefix' in source_folder:
        package_prefix = 'packagePrefix="%s" ' % source_folder['packagePrefix']
      else:
        package_prefix = ''
      xml += '\n      <sourceFolder url="%(url)s" isTestSource="%(is_test_source)s" %(package_prefix)s/>' % {
               'url': source_folder['url'],
               'is_test_source': str(source_folder['isTestSource']).lower(),
               'package_prefix': package_prefix
             }
    for exclude_folder in module['excludeFolders']:
      xml += '\n      <excludeFolder url="%s" />' % exclude_folder['url']
    xml += '\n    </content>'

    xml = add_annotation_generated_source_folder(xml, module)

    # Empirically, if there is one source folder, then the <content> element for the
    # buck-out/android/gen folder should be listed after the other source folders.
    if num_source_folders <= 1:
      xml = add_buck_android_source_folder(xml, module)

    # Dependencies.
    dependencies = module['dependencies']
    module_name = module['name']

    # We need to filter out some of the modules in the dependency list:
    # (1) The module may list itself as a dependency with scope="TEST", which is bad.
    # (2) The module may list another module as a dependency with both COMPILE and TEST scopes, in
    #     which case the COMPILE scope should win.

    # compile_dependencies will be the set of names of dependent modules that do not have scope="TEST"
    compile_dependencies = filter(lambda dep: dep['type'] == 'module' and
        ((not ('scope' in dep)) or dep['scope'] != 'TEST'),
        dependencies)
    compile_dependencies = map(lambda dep: dep['moduleName'], compile_dependencies)
    compile_dependencies = set(compile_dependencies)

    # Filter dependencies to satisfy (1) and (2) defined above.
    filtered_dependencies = []
    for dep in dependencies:
      if dep['type'] != 'module':
        # Non-module dependencies should still be included.
        filtered_dependencies.append(dep)
      else:
        # dep must be a module
        dep_module_name = dep['moduleName']
        if dep_module_name == module_name:
          # Exclude self-references!
          continue
        elif 'scope' in dep and dep['scope'] == 'TEST':
          # If this is a scope="TEST" module and the module is going to be included as
          # a scope="COMPILE" module, then exclude it.
          if not (dep_module_name in compile_dependencies):
            filtered_dependencies.append(dep)
        else:
          # Non-test modules should still be included.
          filtered_dependencies.append(dep)

    # Now that we have filtered the dependencies, we can convert the remaining ones directly into
    # XML.
    excluded_deps_names = set()

    if module_type == 'PLUGIN_MODULE':
      # all the jars below are parts of IntelliJ SDK and even though they are required
      # for language plugins to work standalone, they cannot be included as the plugin
      # module dependency because they would clash with IntelliJ
      excluded_deps_names = set([
        'annotations',    # org/intellij/lang/annotations, org/jetbrains/annotations
        'extensions',     # com/intellij/openapi/extensions/
        'idea',           # org/intellij, com/intellij
        'jdom',           # org/jdom
        'junit',          # junit/
        'light_psi_all',  # light psi library
        'openapi',        # com/intellij/openapi
        'picocontainer',  # org/picocontainer
        'trove4j',        # gnu/trove
        'util',           # com/intellij/util
      ])

    for dep in filtered_dependencies:
      if 'scope' in dep:
        dep_scope = 'scope="%s" ' % dep['scope']
      else:
        dep_scope = ''

      dep_type = dep['type']
      if dep_type == 'library':
        if dep['name'] in excluded_deps_names:
          continue

        xml += '\n    <orderEntry type="library" exported="" %sname="%s" level="project" />' % (dep_scope, dep['name'])
      elif dep_type == 'module':
        dep_module_name = dep['moduleName']

        # TODO(mbolin): Eliminate this special-case for jackson. It exists because jackson is not
        # an ordinary module: it is a module that functions as a library. Project.java should add it
        # as such in project.json to eliminate this special case.
        if dep_module_name == 'module_first_party_orca_third_party_jackson':
          exported = 'exported="" '
        else:
          exported = ''
        xml += '\n    <orderEntry type="module" module-name="%s" %s%s/>' % (dep_module_name, exported, dep_scope)
      elif dep_type == 'inheritedJdk':
        xml += '\n    <orderEntry type="inheritedJdk" />'
      elif dep_type == 'jdk':
        xml += '\n    <orderEntry type="jdk" jdkName="%s" jdkType="%s" />' % (dep['jdkName'], dep['jdkType'])
      elif dep_type == 'sourceFolder':
        xml += '\n    <orderEntry type="sourceFolder" forTests="false" />'

    # Close source code and libraries component.
    xml += '\n  </component>'

    # Close XML.
    xml += MODULE_XML_END

    # Write the module to a file.
    write_file_if_changed(module['pathToImlFile'], xml)


def add_buck_android_source_folder(xml, module):
  # Apparently if we write R.java and friends to a gen/ directory under buck-out/android/ then
  # IntelliJ wants that to be included as a separate source root.
  if 'moduleGenPath' in module:
    xml += '\n    <content url="file://$MODULE_DIR$%s">' % module['moduleGenPath']
    xml += '\n      <sourceFolder url="file://$MODULE_DIR$%s" isTestSource="false" />' % module['moduleGenPath'] 
    xml += '\n    </content>'
  return xml

def add_annotation_generated_source_folder(xml, module):
  if 'annotationGenPath' in module:
    annotation_gen_is_for_test = 'annotationGenIsForTest' in module and module['annotationGenIsForTest']
    is_test_source = str(annotation_gen_is_for_test).lower()

    xml += '\n    <content url="file://$MODULE_DIR$%s">' % module['annotationGenPath']
    xml += '\n      <sourceFolder url="file://$MODULE_DIR$%s" isTestSource="%s" />' % (module['annotationGenPath'], is_test_source)
    xml += '\n    </content>'
  return xml

def write_all_modules(modules):
  """Writes a modules.xml file that defines all of the modules in the project."""
  # Build up the XML.
  xml = ALL_MODULES_XML_START

  # Alpha-sort modules by path before writing them out.
  # This ensures that the ordering within modules.xml is stable.
  modules.sort(key=lambda module: module['pathToImlFile'])

  for module in modules:
    relative_path = module['pathToImlFile']
    xml += '\n      <module fileurl="file://$PROJECT_DIR$/%s" filepath="$PROJECT_DIR$/%s" />' % (relative_path, relative_path)
  xml += ALL_MODULES_XML_END

  # Write the modules to a file.
  write_file_if_changed('.idea/modules.xml', xml)


def write_libraries(libraries):
  """Writes an XML file to define each library."""
  mkdir_p('.idea/libraries')
  for library in libraries:
    # Build up the XML.
    name = library['name']
    xml = LIBRARY_XML_START % {
            'name': name,
            'binary_jar': library['binaryJar'],
          }

    if 'javadocUrl' in library:
      xml += LIBRARY_XML_WITH_JAVADOC % {'javadoc_url': library['javadocUrl']}
    else:
      xml += LIBRARY_XML_NO_JAVADOC

    if 'sourceJar' in library:
      xml += LIBRARY_XML_WITH_SOURCES % {'source_jar': library['sourceJar']}
    else:
      xml += LIBRARY_XML_NO_SOURCES

    xml += LIBRARY_XML_END

    # Write the library to a file
    write_file_if_changed('.idea/libraries/%s.xml' % name, xml)


def write_run_configs():
    """Writes the run configurations that should be available"""
    mkdir_p('.idea/runConfigurations')

    xml = RUN_CONFIG_XML_START
    xml += REMOTE_RUN_CONFIG_XML % {'name': "Debug Buck test"}
    xml += RUN_CONFIG_XML_END
    write_file_if_changed('.idea/runConfigurations/Debug_Buck_test.xml', xml)


def write_file_if_changed(path, content):
  PROJECT_FILES.add(path)
  if os.path.exists(path):
    file_content_as_string = open(path, 'r').read()
    needs_update = content.strip() != file_content_as_string.strip()
  else:
    needs_update = True
  if needs_update:
    out = open(path, 'wb')
    out.write(content)
    MODIFIED_FILES.append(path)


def mkdir_p(path):
  """Runs the equivalent of `mkdir -p`
  Taken from http://stackoverflow.com/questions/600268/mkdir-p-functionality-in-python
  Args:
    path: an absolute path
  """
  try:
    os.makedirs(path)
  except OSError as exc:
    if exc.errno == errno.EEXIST:
      pass
    else: raise

def clean_old_files():
  if os.path.isdir('.git'):
    try:
      files_to_clean = subprocess.check_output(['git', 'ls-files', '--other'])
      for file_name in files_to_clean.splitlines():
        if file_name.endswith('.iml') and file_name not in PROJECT_FILES:
          os.remove(file_name)
      return
    except Exception as e:
      pass


if __name__ == '__main__':
  if not os.path.isdir('.git'):
    for root, dirnames, filenames in os.walk('.'):
      if fnmatch.filter(filenames, '*.iml'):
        sys.stderr.write('\n'.join(
          [ '  ::  "buck project" run from a directory not under Git source',
            '  ::  control.  If invoking buck project with an argument, we are',
            '  ::  not able to remove old .iml files, which can result in',
            '  ::  IntelliJ being in a bad state.  Please close and re-open',
            '  ::  IntelliJ if it\'s open.' ]))
        sys.stderr.flush()
        break

  json_file = sys.argv[1]
  parsed_json = json.load(open(json_file, 'r'))

  libraries = parsed_json['libraries']
  write_libraries(libraries)

  modules = parsed_json['modules']
  write_modules(modules)
  write_all_modules(modules)
  write_run_configs()
  if PROJECT_FILES:
    clean_old_files()

  # Write the list of modified files to stdout
  for path in MODIFIED_FILES: print path
