<commit_before>/*
 * User: anna
 * Date: 26-Jun-2007
 */
package com.intellij.codeInsight;

import com.intellij.CommonBundle;
import com.intellij.ide.util.PropertiesComponent;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.Result;
import com.intellij.openapi.command.WriteCommandAction;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.fileChooser.FileChooser;
import com.intellij.openapi.fileChooser.FileChooserDescriptor;
import com.intellij.openapi.fileChooser.FileChooserDescriptorFactory;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.project.ProjectBundle;
import com.intellij.openapi.projectRoots.ProjectRootType;
import com.intellij.openapi.projectRoots.SdkModificator;
import com.intellij.openapi.roots.*;
import com.intellij.openapi.roots.libraries.Library;
import com.intellij.openapi.ui.Messages;
import com.intellij.openapi.util.Comparing;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.*;
import com.intellij.psi.util.PsiFormatUtil;
import com.intellij.psi.xml.XmlDocument;
import com.intellij.psi.xml.XmlFile;
import com.intellij.psi.xml.XmlTag;
import com.intellij.util.ArrayUtil;
import com.intellij.util.IncorrectOperationException;
import com.intellij.util.ui.OptionsMessageDialog;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import javax.swing.*;
import java.io.IOException;
import java.util.List;

public class ExternalAnnotationsManagerImpl extends ExternalAnnotationsManager {
  private static final Logger LOG = Logger.getInstance("#" + ExternalAnnotationsManagerImpl.class.getName());

  @NonNls private static final String EXTERNAL_ANNOTATIONS_PROPERTY = "ExternalAnnotations";

  @Nullable
  public PsiAnnotation findExternalAnnotation(final PsiModifierListOwner listOwner, final String annotationFQN) {
    final XmlFile xmlFile = findExternalAnnotationsFile(listOwner);
    if (xmlFile != null) {
      final XmlDocument document = xmlFile.getDocument();
      if (document != null) {
        final XmlTag rootTag = document.getRootTag();
        if (rootTag != null) {
          final String externalName = PsiFormatUtil.getExternalName(listOwner);
          for (final XmlTag tag : rootTag.getSubTags()) {
            final String className = tag.getAttributeValue("name");
            if (Comparing.strEqual(className, externalName)) {
              for (XmlTag annotationTag : tag.getSubTags()) {
                if (Comparing.strEqual(annotationTag.getAttributeValue("name"), annotationFQN)) {
                  StringBuffer buf = new StringBuffer();
                  for (XmlTag annotationaParameter : annotationTag.getSubTags()) {
                    buf.append(",").append(annotationaParameter.getAttributeValue("name")).append("=")
                      .append(annotationaParameter.getAttributeValue("value"));
                  }
                  final String annotationText =
                    "@" + annotationFQN + (buf.length() > 0 ? "(" + StringUtil.trimStart(buf.toString(), ",") + ")" : "");
                  try {
                    return listOwner.getManager().getElementFactory().createAnnotationFromText(annotationText, null);
                  }
                  catch (IncorrectOperationException e) {
                    LOG.error(e);
                  }
                }
              }
              break;
            }
          }
        }
      }
    }
    return null;
  }


  public void annotateExternally(final PsiModifierListOwner listOwner, final String annotationFQName) {
    final Project project = listOwner.getProject();
    final PsiManager psiManager = listOwner.getManager();
    XmlFile xmlFile = findExternalAnnotationsFile(listOwner);
    if (xmlFile != null) {
      if (!CodeInsightUtil.prepareFileForWrite(xmlFile)) return;
      annotateExternally(listOwner, annotationFQName, xmlFile);
    }
    else {
      final PsiFile containingFile = listOwner.getContainingFile();
      if (containingFile instanceof PsiJavaFile) {
        final String packageName = ((PsiJavaFile)containingFile).getPackageName();
        final VirtualFile virtualFile = containingFile.getVirtualFile();
        LOG.assertTrue(virtualFile != null);
        final List<OrderEntry> entries = ProjectRootManager.getInstance(project).getFileIndex().getOrderEntriesForFile(virtualFile);
        if (!entries.isEmpty()) {
          final OrderEntry entry = entries.get(0);
          if (ApplicationManager.getApplication().isUnitTestMode() || ApplicationManager.getApplication().isHeadlessEnvironment()) return;
          SwingUtilities.invokeLater(new Runnable() {
            public void run() {
              final FileChooserDescriptor descriptor = FileChooserDescriptorFactory.createSingleFolderDescriptor();
              descriptor.setTitle(ProjectBundle.message("external.annotations.root.chooser.title", entry.getPresentableName()));
              descriptor.setDescription(ProjectBundle.message("external.annotations.root.chooser.description"));
              final VirtualFile[] files = FileChooser.chooseFiles(project, descriptor);
              if (files.length > 0) {
                new WriteCommandAction(project, null) {
                  protected void run(final Result result) throws Throwable {
                    if (files[0] != null) {
                      appendChosenAnnotationsRoot(entry, files[0]);
                      annotateExternally(listOwner, annotationFQName, createAnnotationsXml(psiManager, files[0], packageName));
                    }
                  }<commit_msg>do not force to open editor with external annotations<commit_after>/*
 * User: anna
 * Date: 26-Jun-2007
 */
package com.intellij.codeInsight;

import com.intellij.CommonBundle;
import com.intellij.ide.util.PropertiesComponent;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.Result;
import com.intellij.openapi.command.WriteCommandAction;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.fileChooser.FileChooser;
import com.intellij.openapi.fileChooser.FileChooserDescriptor;
import com.intellij.openapi.fileChooser.FileChooserDescriptorFactory;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.project.ProjectBundle;
import com.intellij.openapi.projectRoots.ProjectRootType;
import com.intellij.openapi.projectRoots.SdkModificator;
import com.intellij.openapi.roots.*;
import com.intellij.openapi.roots.libraries.Library;
import com.intellij.openapi.ui.Messages;
import com.intellij.openapi.util.Comparing;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.openapi.vfs.ReadonlyStatusHandler;
import com.intellij.psi.*;
import com.intellij.psi.util.PsiFormatUtil;
import com.intellij.psi.xml.XmlDocument;
import com.intellij.psi.xml.XmlFile;
import com.intellij.psi.xml.XmlTag;
import com.intellij.util.ArrayUtil;
import com.intellij.util.IncorrectOperationException;
import com.intellij.util.ui.OptionsMessageDialog;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import javax.swing.*;
import java.io.IOException;
import java.util.List;

public class ExternalAnnotationsManagerImpl extends ExternalAnnotationsManager {
  private static final Logger LOG = Logger.getInstance("#" + ExternalAnnotationsManagerImpl.class.getName());

  @NonNls private static final String EXTERNAL_ANNOTATIONS_PROPERTY = "ExternalAnnotations";

  @Nullable
  public PsiAnnotation findExternalAnnotation(final PsiModifierListOwner listOwner, final String annotationFQN) {
    final XmlFile xmlFile = findExternalAnnotationsFile(listOwner);
    if (xmlFile != null) {
      final XmlDocument document = xmlFile.getDocument();
      if (document != null) {
        final XmlTag rootTag = document.getRootTag();
        if (rootTag != null) {
          final String externalName = PsiFormatUtil.getExternalName(listOwner);
          for (final XmlTag tag : rootTag.getSubTags()) {
            final String className = tag.getAttributeValue("name");
            if (Comparing.strEqual(className, externalName)) {
              for (XmlTag annotationTag : tag.getSubTags()) {
                if (Comparing.strEqual(annotationTag.getAttributeValue("name"), annotationFQN)) {
                  StringBuffer buf = new StringBuffer();
                  for (XmlTag annotationaParameter : annotationTag.getSubTags()) {
                    buf.append(",").append(annotationaParameter.getAttributeValue("name")).append("=")
                      .append(annotationaParameter.getAttributeValue("value"));
                  }
                  final String annotationText =
                    "@" + annotationFQN + (buf.length() > 0 ? "(" + StringUtil.trimStart(buf.toString(), ",") + ")" : "");
                  try {
                    return listOwner.getManager().getElementFactory().createAnnotationFromText(annotationText, null);
                  }
                  catch (IncorrectOperationException e) {
                    LOG.error(e);
                  }
                }
              }
              break;
            }
          }
        }
      }
    }
    return null;
  }


  public void annotateExternally(final PsiModifierListOwner listOwner, final String annotationFQName) {
    final Project project = listOwner.getProject();
    final PsiManager psiManager = listOwner.getManager();
    XmlFile xmlFile = findExternalAnnotationsFile(listOwner);
    if (xmlFile != null) {
      if (ReadonlyStatusHandler.getInstance(project).ensureFilesWritable(xmlFile.getVirtualFile()).hasReadonlyFiles()) return;
      annotateExternally(listOwner, annotationFQName, xmlFile);
    }
    else {
      final PsiFile containingFile = listOwner.getContainingFile();
      if (containingFile instanceof PsiJavaFile) {
        final String packageName = ((PsiJavaFile)containingFile).getPackageName();
        final VirtualFile virtualFile = containingFile.getVirtualFile();
        LOG.assertTrue(virtualFile != null);
        final List<OrderEntry> entries = ProjectRootManager.getInstance(project).getFileIndex().getOrderEntriesForFile(virtualFile);
        if (!entries.isEmpty()) {
          final OrderEntry entry = entries.get(0);
          if (ApplicationManager.getApplication().isUnitTestMode() || ApplicationManager.getApplication().isHeadlessEnvironment()) return;
          SwingUtilities.invokeLater(new Runnable() {
            public void run() {
              final FileChooserDescriptor descriptor = FileChooserDescriptorFactory.createSingleFolderDescriptor();
              descriptor.setTitle(ProjectBundle.message("external.annotations.root.chooser.title", entry.getPresentableName()));
              descriptor.setDescription(ProjectBundle.message("external.annotations.root.chooser.description"));
              final VirtualFile[] files = FileChooser.chooseFiles(project, descriptor);
              if (files.length > 0) {
                new WriteCommandAction(project, null) {
                  protected void run(final Result result) throws Throwable {
                    if (files[0] != null) {
                      appendChosenAnnotationsRoot(entry, files[0]);
                      annotateExternally(listOwner, annotationFQName, createAnnotationsXml(psiManager, files[0], packageName));
                    }
                  }
{'fraction_non_alphanumeric': 0.09981913702523469, 'fraction_numerical': 0.002067005425889243, 'mean_word_length': 3.294378698224852, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 9, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 20}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1221985', 'n_tokens_mistral': 3186, 'n_tokens_neox': 3055, 'n_words': 558}