2010-10-17 2 views
1

Приветствия, Я не мог предоставить все детали в вопросе, так что вот ключевые сведения.Как я могу избежать узких мест при использовании jni в веб-приложении/службе java

У меня есть родная dll (и соответствующая .so) упаковка статической библиотеки, которая создается языком программирования Eiffel. Я написал обертку C++ вокруг статической библиотеки, и я успешно открыл ее для Java. Однако, если я использую эту dll в веб-приложении, все станет довольно сложным. Проблема состоит в том, что несколько потоков java будут обращаться к одному и тому же C++-коду, где внутренний контекст (?) Поддерживается между вызовами разных классов & экземпляров. Чтобы использовать функциональность из кода Эйфеля, нужно инициализировать время выполнения Eiffel из C++, а затем использовать библиотеки Eiffel, чтобы использовать классы Eiffel из C++. К сожалению, это означает, что все входящие запросы на стороне сервера Java заканчиваются в одном месте на C++ (внутри собственной DLL), где есть только одно время выполнения Eiffel. Эта ситуация заставляет меня сделать весь поток среды Eiffel безопасным, и только одна операция одним потоком Java может использовать код Эйфеля, проходя через JNI. У меня такое ощущение, что это может быстро стать проблемой масштабируемости.

Я чувствую, что мне может понадобиться пул процессов, каждый из которых загружает копию той же DLL (или .so под * nix), которая будет передаваться входящим потокам с Java. Таким образом, после загрузки общей библиотеки код C++ создаст, скажем, 10 процессов, а входящие потоки со стороны Java будут выделены для этих процессов с помощью кода на C++. Поток событий будет таким:

Java-поток обращается к собственному коду (C++) в общей библиотеке. Native код проверяет, какие процессы доступны из технологического бассейна делает использование одного из процессов через МПК, пометив его занят (возможно, используя нить?)

Это единственная кросс-платформенный, как я мог думать, чтобы безопасно загружать одну и ту же часть кода (Eiffel runtime и классы eiffel) без каких-либо проблем с безопасностью потоков.

Это все из-за того, что Eiffel runtime является дорогостоящим и глобальным компонентом, который я должен предоставить через JNI.

Или я должен просто выполнять операции с потоками, где в любой момент может подаваться только один поток от JNI? Есть ли какой-либо трюк, который я могу сделать с Java для создания легких изолированных контейнеров jvm, каждый из которых использует только одно Eiffel runtime?

Ваш отзыв будет высоко оценен.

С наилучшими пожеланиями Şeref

ответ

1

Первый вопрос: если у вас несколько копий DLL, загруженных в отдельных процессах они будут работать правильно? Предполагая, что «да», ваша идея иметь несколько копий, работающих под звуки, может иметь потенциал. (На самом деле, есть еще один вопрос: сначала я предполагаю, что повторная реализация Eiffel на Java уже была проверена и оказалась слишком сложной?)

Мое желание сначала было проверить, один, поточно-безопасный подход может дать достаточно хорошую производительность. Если это не так, и вам нужна масштабируемость, тогда еще одна возможность - рассмотреть возможность использования нескольких дешевых мешков (или виртуальных машин) - у этого есть большая заслуга простоты. Это не требует больших усилий по разработке, чтобы стоить больше, чем несколько машин.

В противном случае ваше представление о пуле «сервисных» процессов звучит как разумная идея.Существует множество возможностей для взаимодействия между процессами (IPC). Почти по определению вы тратите много времени на обслуживание в каждом вызове (иначе у вас возникнет проблема?), Поэтому в этом случае реальный механизм IPC не должен быть сильно оптимизирован - это простота и простота администрирования. Сначала я хотел бы взглянуть на подход на основе очереди с использованием JMS - да, есть много других опций, включая RMI или низкоуровневые сокеты, но JMS имеет два преимущества: это очень простой и масштабируемый вид, из которого запросчик просто выдает сообщения на очереди, никогда не нужно знать, сколько может быть процессов обслуживания. Также интересно, что на некоторых платформах поставщиков есть реализации C++ для JMS (XMS - это тот, который я использую), и, следовательно, вы даже не использовали Java в процессе обслуживания.

Выработать: начальная позиция

WS-Client ---WS Call ---> WS in Web App ---JNI--->C++/Eiffel 

Я предлагаю использовать

WS-Client ---WS Call ---> WS in Web App --JMS enq--> Q --JMS deq--> Java---JNI--->C++/Eiffel 

или

WS-Client ---WS Call ---> WS in Web App --JMS enq--> Q --XMS deq--->C++/Eiffel 

Ответы могут быть возвращены на temparary очереди ответов с сообщением запроса содержит Ответ на имя Q и информацию о корреляции.

Как это бывает, этот последний шаблон - это то, что делает мое текущее приложение, с хорошей производительностью. Я думаю, что отсутствие Java в движке C++/Eiffel может быть победой. Если это псевдосинхронное использование JMS кажется непривлекательным, то моей альтернативой было бы использовать EJB с удаленными интерфейсами. Идея опять-таки заключается в том, чтобы вложить всю работу по масштабируемости в инфраструктуру.

+0

База данных Эйфелевой башни огромна, и у нее нет шансов переписать ее на данный момент. Я искал способ создания множества jvms для песочницы, или экземпляров сервера приложений, которые все используют изолированную dll для потока в фоновом режиме. Я не вижу, как я могу использовать JMS с входящим запросом веб-службы, который должен подключиться к концу jni, не могли бы вы объяснить это немного больше? Спасибо за ответ в любом случае. – mahonya

+0

Я немного расширился. Мы используем этот шаблон с некоторым успехом. – djna

+0

Выглядит многообещающе, спасибо за обновление. Я не уверен, что могу получить механизм, чтобы вернуть ответ. Я бы, вероятно, заставил вызов веб-службы ждать, пока он не получит ответ на свой запрос из очереди jms. Вероятно, это лучший способ обеспечить безопасность потоков, не вникая в специфику механизмов безопасности потоков C++ или JNI. – mahonya

 Смежные вопросы

  • Нет связанных вопросов^_^