A comprehensive Python-to-Java bridge enabling seamless integration between Python and Java virtual machines
—
Quality
Pending
Does it follow best practices?
Impact
Pending
No eval scenarios have been run
Specialized functionality including threading support, GUI integration, NIO buffer support, customization framework, and database API integration. This module covers JPype's advanced features for complex integration scenarios.
Java-style synchronization primitives for thread-safe operations.
def synchronized(obj):
"""Create Java monitor lock for with statements.
Args:
obj: Java object to synchronize on
Returns:
Context manager for synchronization block
Example:
with synchronized(java_object):
# Thread-safe operations
java_object.modify()
"""Convert Python objects to Java NIO buffers for high-performance operations.
def convertToDirectBuffer(obj):
"""Convert arrays/buffers to Java NIO direct buffers.
Args:
obj: Python array, bytes, or buffer-like object
Returns:
Java NIO Buffer: Direct buffer for efficient Java operations
Raises:
TypeError: If object cannot be converted to buffer
"""Platform-specific GUI environment configuration (macOS/Darwin specific).
def setupGuiEnvironment(cb):
"""Setup GUI environment for Java Swing/AWT applications.
Args:
cb: Callback function for GUI setup
Note:
Darwin/macOS specific functionality
"""
def shutdownGuiEnvironment():
"""Shutdown GUI environment.
Note:
Darwin/macOS specific functionality
"""Advanced customization system for extending JPype's type handling.
class JImplementationFor:
"""Decorator for registering class implementations for Java types.
Allows Python classes to serve as implementations for Java types.
"""
def __init__(self, classname: str, base: bool = False):
"""Create implementation decorator.
Args:
classname: Java class name to implement
base: Whether this is a base implementation
"""
class JConversion:
"""Decorator for registering type conversions.
Allows custom conversion between Python and Java types.
"""
def __init__(self, cls, **kwargs):
"""Create conversion decorator.
Args:
cls: Target class for conversion
**kwargs: Additional conversion options
"""SQL database API 2.0 constants and type definitions for JDBC integration.
# SQL Type Constants (from jpype.dbapi2)
ARRAY: int
ASCII_STREAM: int
BIGINT: int
BINARY: int
BINARY_STREAM: int
BIT: int
BLOB: int
BOOLEAN: int
CHAR: int
CHARACTER_STREAM: int
CLOB: int
DATE: int
DATETIME: int
DECIMAL: int
DISTINCT: int
DOUBLE: int
FLOAT: int
INTEGER: int
JAVA_OBJECT: int
LONGNVARCHAR: int
LONGVARBINARY: int
LONGVARCHAR: int
NCHAR: int
NCHARACTER_STREAM: int
NCLOB: int
NULL: int
NUMBER: int
NUMERIC: int
NVARCHAR: int
OBJECT: int
OTHER: int
REAL: int
REF: int
RESULTSET: int
ROWID: int
SMALLINT: int
SQLXML: int
STRING: int
STRUCT: int
TEXT: int
TIME: int
TIMESTAMP: int
TIMESTAMP_WITH_TIMEZONE: int
TIME_WITH_TIMEZONE: int
TINYINT: int
URL: int
VARBINARY: int
VARCHAR: int
# Additional Database API classes and functions
class Connection: ...
class Cursor: ...
def connect(*args, **kwargs): ...
apilevel: str # "2.0"
threadsafety: int # 2
paramstyle: str # "qmark"import jpype
import threading
import time
jpype.startJVM()
# Create shared Java object
shared_list = jpype.java.util.ArrayList()
def worker_thread(thread_id):
"""Worker thread that modifies shared Java object safely."""
for i in range(5):
# Synchronize access to Java object
with jpype.synchronized(shared_list):
current_size = shared_list.size()
time.sleep(0.01) # Simulate work
shared_list.add(f"Thread-{thread_id}-Item-{i}")
print(f"Thread {thread_id}: Added item, size now {shared_list.size()}")
# Create multiple Python threads
threads = []
for i in range(3):
thread = threading.Thread(target=worker_thread, args=(i,))
threads.append(thread)
thread.start()
# Wait for all threads to complete
for thread in threads:
thread.join()
print(f"Final list size: {shared_list.size()}")
print("List contents:")
for i in range(shared_list.size()):
print(f" {i}: {shared_list.get(i)}")
jpype.shutdownJVM()import jpype
import array
import numpy as np
jpype.startJVM()
# Convert Python array to Java NIO buffer
python_array = array.array('i', [1, 2, 3, 4, 5])
java_buffer = jpype.convertToDirectBuffer(python_array)
print(f"Buffer type: {java_buffer.getClass().getName()}")
print(f"Buffer capacity: {java_buffer.capacity()}")
print(f"Buffer remaining: {java_buffer.remaining()}")
# Read from buffer
values = []
while java_buffer.hasRemaining():
values.append(java_buffer.get())
print(f"Buffer contents: {values}")
# Reset buffer position
java_buffer.rewind()
# Use with Java NIO operations
FileChannel = jpype.JClass("java.nio.channels.FileChannel")
# Example: could write buffer to file channel
# Convert NumPy array to buffer (if NumPy available)
try:
import numpy as np
numpy_array = np.array([10, 20, 30, 40, 50], dtype=np.int32)
numpy_buffer = jpype.convertToDirectBuffer(numpy_array)
print(f"NumPy buffer capacity: {numpy_buffer.capacity()}")
except ImportError:
print("NumPy not available for buffer conversion example")
jpype.shutdownJVM()import jpype
from jpype import JImplementationFor, JConversion
jpype.startJVM()
# Custom implementation for Java Iterator
@JImplementationFor("java.util.Iterator")
class PythonListIterator:
"""Python implementation of Java Iterator interface."""
def __init__(self, python_list):
self.items = python_list
self.index = 0
def hasNext(self):
return self.index < len(self.items)
def next(self):
if not self.hasNext():
raise jpype.java.util.NoSuchElementException()
item = self.items[self.index]
self.index += 1
return item
# Custom conversion for Python datetime to Java Date
import datetime
@JConversion(jpype.java.util.Date)
class DateTimeConverter:
"""Convert Python datetime to Java Date."""
@staticmethod
def convert(py_datetime):
if isinstance(py_datetime, datetime.datetime):
timestamp_ms = int(py_datetime.timestamp() * 1000)
return jpype.java.util.Date(timestamp_ms)
return py_datetime
# Use custom implementations
python_list = ["apple", "banana", "cherry"]
iterator = PythonListIterator(python_list)
# Java code can use our Python iterator
while iterator.hasNext():
print(f"Next item: {iterator.next()}")
jpype.shutdownJVM()import jpype
from jpype import dbapi2
jpype.startJVM()
# Add JDBC driver to classpath (example)
# jpype.addClassPath("/path/to/jdbc-driver.jar")
# SQL type mapping using dbapi2 constants
sql_type_names = {
dbapi2.VARCHAR: "VARCHAR",
dbapi2.INTEGER: "INTEGER",
dbapi2.BIGINT: "BIGINT",
dbapi2.DECIMAL: "DECIMAL",
dbapi2.BOOLEAN: "BOOLEAN",
dbapi2.DATE: "DATE",
dbapi2.TIMESTAMP: "TIMESTAMP",
dbapi2.BLOB: "BLOB",
dbapi2.CLOB: "CLOB"
}
def map_java_sql_type(java_type_code):
"""Map Java SQL type code to readable name."""
return sql_type_names.get(java_type_code, f"UNKNOWN({java_type_code})")
# Example JDBC operations (requires JDBC driver)
try:
# Load JDBC driver (example)
# driver_class = jpype.JClass("com.example.jdbc.Driver")
# jpype.java.sql.DriverManager.registerDriver(driver_class())
# Example connection (would need real database)
# connection = jpype.java.sql.DriverManager.getConnection("jdbc:example://localhost")
# metadata = connection.getMetaData()
print("SQL type constants available:")
for constant_name in dir(dbapi2):
if constant_name.isupper() and not constant_name.startswith('_'):
value = getattr(dbapi2, constant_name)
if isinstance(value, int):
print(f" {constant_name}: {value}")
except Exception as e:
print(f"JDBC example requires database driver: {e}")
jpype.shutdownJVM()import jpype
import platform
if platform.system() == "Darwin": # macOS only
def gui_callback():
"""Callback for GUI environment setup."""
print("GUI environment initialized")
# Additional GUI setup code here
# Setup GUI before creating Swing components
jpype.startJVM()
jpype.setupGuiEnvironment(gui_callback)
# Now safe to create Swing/AWT components
JFrame = jpype.javax.swing.JFrame
JButton = jpype.javax.swing.JButton
frame = JFrame("Test Window")
button = JButton("Click Me")
frame.add(button)
frame.setSize(300, 200)
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE)
# For actual display, uncomment:
# frame.setVisible(True)
# Cleanup GUI environment
jpype.shutdownGuiEnvironment()
jpype.shutdownJVM()
else:
print("GUI environment setup is macOS-specific")import jpype
import gc
import time
jpype.startJVM()
def performance_test():
"""Test performance optimization techniques."""
# Large object creation test
start_time = time.time()
# Create many Java objects
objects = []
for i in range(10000):
string_obj = jpype.java.lang.String(f"Object {i}")
objects.append(string_obj)
creation_time = time.time() - start_time
print(f"Created 10000 objects in {creation_time:.3f} seconds")
# Memory usage optimization
# Clear Python references
objects.clear()
# Force garbage collection
gc.collect()
# Java garbage collection hint
jpype.java.lang.System.gc()
# Check memory usage
runtime = jpype.java.lang.Runtime.getRuntime()
total_memory = runtime.totalMemory()
free_memory = runtime.freeMemory()
used_memory = total_memory - free_memory
print(f"JVM Memory - Total: {total_memory//1024//1024}MB, " +
f"Used: {used_memory//1024//1024}MB, " +
f"Free: {free_memory//1024//1024}MB")
performance_test()
jpype.shutdownJVM()import jpype
from jpype import JImplements, JOverride
jpype.startJVM()
# Custom exception handler
@JImplements("java.lang.Thread$UncaughtExceptionHandler")
class PythonExceptionHandler:
"""Python implementation of Java UncaughtExceptionHandler."""
@JOverride
def uncaughtException(self, thread, exception):
print(f"Uncaught exception in thread {thread.getName()}: {exception}")
# Could log to Python logging system, send alerts, etc.
# Set global exception handler
handler = PythonExceptionHandler()
jpype.java.lang.Thread.setDefaultUncaughtExceptionHandler(handler)
# Create thread that will throw exception
@JImplements("java.lang.Runnable")
class FailingTask:
@JOverride
def run(self):
raise jpype.java.lang.RuntimeException("This task always fails!")
# Run failing task in Java thread
failing_task = FailingTask()
thread = jpype.java.lang.Thread(failing_task, "FailingThread")
thread.start()
thread.join()
jpype.shutdownJVM()Install with Tessl CLI
npx tessl i tessl/pypi-jpype1