Неправильный Manifest.mf в IntelliJ IDEA создан .jar

102

Я пытаюсь упаковать проект с использованием библиотек OptaPlanner 6.0.1 в .jar через артефакт jar IntelliJ IDEA, но вместо моего manifest.mf, содержащего стандартный

Manifest-Version: 1.0
Main-Class: a.b.c.app

jar использует тот, который поставляется в ecj-3.7.2.jar, одной из поддерживающих библиотек OptaPlanner:

Manifest-Version: 1.0
Build-Jdk: 1.6.0_26
Built-By: ibrandt
Created-By: Apache Maven
Archiver-Version: Plexus Archiver

Из-за этого "no main manifest attribute, in appname.jar"при попытке запустить приложение возникает ошибка. Если я вручную заменю манифест в файле .jar своим, все будет работать правильно. Что я могу сделать, чтобы это исправить?

Я храню библиотеки в отдельном каталоге / lib, и они были добавлены в корень артефакта jar как извлеченный каталог, IntelliJ IDEA - v13.0.1.

Грудольф
источник
1
Вы знаете инструменты сборки, такие как ant, maven или gradle?
MariuszS 06
Я знаю о них, но пока использовал только их аналоги make и .NET (NAnt, MSBuild). Какой из них я должен выбрать, если инструмент сборки IntelliJ не подойдет?
grudolf 06
1
Проголосуйте за исправление этой проблемы здесь ,
bigjosh

Ответы:

260

У меня такая же проблема.

Убедитесь, что ваш MANIFEST.MF находится в:

src/main/resources/META_INF/

НЕ

src/main/java/META_INF/
джамхан
источник
20
Это действительно правильный ответ, похоже, что Intellij IDEA неправильно помещает папку META-INF, когда шаблоном проекта является Maven
Kumait
В моем случае мне пришлось изменить макет моего проекта. Раньше у меня был проект с макетом maven, но я убрал поддержку maven. Я воссоздаю проект с нуля, и теперь он работает.
Maxence
1
У меня это не сработало, мне пришлось переместить файл Mainfest в корень проекта.
racs
Maven настолько глуп, что помещает этот файл не в тот каталог? : ^)
Дарья
@Kumait, проблема все еще существует в IntelliJ 2017.1.5. Мне интересно, знает ли об этом команда JetBrain.
fruqi
12

Исправить:

  1. Файл> Структура проекта
  2. В разделе "Настройки проекта " слева выберите "Артефакты".
  3. Найдите определение JAR на средней панели и выберите его
  4. На левой панели вкладки «Output Layout» найдите файл jar в списке и выберите его.
  5. Внизу нажмите кнопку «Использовать существующий манифест» и выберите файл манифеста, который находится в источнике вашего проекта.
  6. Нажмите ОК и запустите сборку
Джавару
источник
3
Нет кнопки «Использовать существующий манифест», однако файл манифеста в макете вывода указывает на правильное местоположение (... \ src \ main \ java \ META-INF \ MANIFEST.MF)
grudolf
5
Хорошо, пришлось удалить артефакт jar и воссоздать его, на этот раз как «Пустой» вместо «Из модулей с зависимостями». Получил кнопки «Создать манифест» и «Использовать существующий манифест», указывал на мой манифест, читаемые библиотеки и компилирующий вывод. Есть два отличия от предыдущего: файл META_INF \ MANIFEST.INF теперь явно включен в выходной макет, и файл jar создается правильно. :)
grudolf 06
Это не решает проблемы, по крайней мере, для меня. Однако ответ Джамана сработал.
Эндрю Брекса
Комментарий, добавленный пользователем с низким уровнем репутации @ ds-Justice, выглядит следующим образом - комментарий @grudolf выше о создании пустого Jar-файла был единственным, что сработало для меня после нескольких часов борьбы с импортированным проектом Gradle. Это важный вопрос, пожалуйста, рассмотрите возможность репоста вашего комментария как отдельного ответа.
Шон Механ
10

Как указано в комментарии @grudolf в одном из других ответов, один из способов сделать это (и единственный, который работал у меня в импортированном проекте Gradle) - создать пустую банку следующим образом:

  • Структура проекта -> Артефакты -> + Jar -> Пусто
  • На центральной панели теперь есть кнопки «Создать манифест» и «Использовать существующий манифест». Воспользуйтесь одним из них.
  • Мне было трудно извлекать зависимые библиотеки с их собственными манифестами в выходной корень, они, казалось, периодически перезаписывали новый созданный вручную манифест. Казалось, что возня с порядком действий заставила это работать.

ОБНОВИТЬ:

Это определенно ошибка в Idea. Этот связанный ответ надежно работает, когда есть извлеченные каталоги. В сущности, вы найдете .idea / JARNAME.xml, добавьте добавить следующий элемент в самом верху этого <root>элемента для вашей баночки. Любые извлеченные элементы над вашей новой копией файла, которые содержат манифест, будут уничтожать ваш новый манифест.

  <element id="directory" name="/META-INF">
    <element id="file-copy" path="$PROJECT_DIR$/modulename/src/META-INF/MANIFEST.MF" />
  </element>
Осень
источник
7

Если вы хотите указать основной класс, вам нужно добавить этот плагин в pom.xml:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-jar-plugin</artifactId>
    <version>2.6</version>
    <configuration>
        <archive>
            <manifest>
                <mainClass>Form</mainClass>
            </manifest>
        </archive>
    </configuration>
</plugin>
usbo
источник
1

У меня была похожая проблема.

Проблема была в файле pom.xml.

<archive>
  <manifestEntries>
    <Dependencies>one.jar,
                  two.rar, 
                  other.jar
    </Dependencies>
  </manifestEntries>
</archive>

Я не знаю, по какой причине этот код работает в eclipse, но не в IntelliJ

Это правильно.

<archive>
  <manifestEntries>
    <Dependencies>one.jar, two.rar, other.jar</Dependencies>
  </manifestEntries>
</archive>

Manifest.mf сработал !!!

Надеюсь, это поможет.

Marcelocesar
источник
У меня была именно такая ситуация, и я пришел к такому же выводу, что и вы: новые строки между элементами <Dependencies> работали в Eclipse, но не в Intellij IDEA.
Арион Краузе
0

Есть несколько способов создания исполняемых jar-файлов. Использование функции графического интерфейса IntelliJ - хороший способ. Другой способ - использовать Maven (или аналогично в gradle, buildr и т. Д.), Который удобен для сборки-сервера:

Это более или менее скопировать и вставить из примеров сборки maven optaplanner:

  1. Jar конечного пользователя (optaplanner-examples - *. Jar) должен включать в свой манифест путь к классам своих зависимостей .
  2. Затем скрипт sh и bat должен запустить этот jar с соответствующим.
Джеффри Де Смет
источник
0

Чтобы не было проблем, подобных Manifest, у вас должен быть каталог с именем «META-INF» в каталоге «src». Итак, создайте его и поместите в него файл с именем «MANIFEST.MF» со следующим содержимым:

Manifest-Version: 1.0
Main-Class: <packageName>.Main

Не забыть заменить имя пакета, содержащего основной класс выше!

Мохсен Абаси
источник
5
В записи указано, что я удалил религиозные материалы из вашего сообщения в августе. Обратите внимание, что сообщество обсуждало добавление религиозных тем в сообщения, и ответ заключается в том, что мы предпочли бы, чтобы они не учитывались. Тем не менее, вы можете добавить их в свой профиль или на аватар.
Halfer