Class: JavaClass::ClassList::JarSearcher

Inherits:
Object
  • Object
show all
Defined in:
lib/javaclass/classlist/jar_searcher.rb

Overview

Search in zip or jar files for Java class files, check for package access or inner classes and call back a list of all these.

Author

Peter Kofler

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initializeJarSearcher

Create a new searcher.



16
17
18
19
20
# File 'lib/javaclass/classlist/jar_searcher.rb', line 16

def initialize
  @skip_inner_classes = true
  @skip_package_classes = false
  @package_filters = []
end

Instance Attribute Details

#skip_inner_classesObject

Returns the value of attribute skip_inner_classes.



12
13
14
# File 'lib/javaclass/classlist/jar_searcher.rb', line 12

def skip_inner_classes
  @skip_inner_classes
end

#skip_package_classesObject

Returns the value of attribute skip_package_classes.



13
14
15
# File 'lib/javaclass/classlist/jar_searcher.rb', line 13

def skip_package_classes
  @skip_package_classes
end

Instance Method Details

#compile_list(version, path, list) ⇒ Object

Compile the class list for the given version of Java. This searches the path for zips and jars and adds them to the given list of found classes. version is a number >= 0, e.g. 2 for JDK 1.2. list must provide a add_class(entry, is_public, version) method.



53
54
55
56
57
58
59
60
61
62
63
64
# File 'lib/javaclass/classlist/jar_searcher.rb', line 53

def compile_list(version, path, list)
  cpe = JavaClass::Classpath::CompositeClasspath.new
  cpe.find_jars(path)
  filter_classes(cpe.names).each do |entry|
    is_public = public?(cpe, entry)
    next if @skip_package_classes && !is_public
    list.add_class(entry, is_public, version) if list
    yield(entry, is_public, version) if block_given?
  end
  
  list
end

#filter_classes(classes) ⇒ Object

Return the list of classnames of this list of classes . Skips inner classes if skip_inner_classes is true. Skips classes that are in the filtered packages.



31
32
33
34
35
# File 'lib/javaclass/classlist/jar_searcher.rb', line 31

def filter_classes(classes)
  classes.find_all do |name|
    !(@skip_inner_classes && name =~ /\$/) && (@package_filters.find { |filter| name =~ filter } == nil)
  end
end

#filters=(filters) ⇒ Object

The given filters will be dropped during searching. filters contain the beginning of package paths, i.e. com/sun/.



24
25
26
# File 'lib/javaclass/classlist/jar_searcher.rb', line 24

def filters=(filters)
  @package_filters = filters.collect{ |f| /^#{f}/ }
end

#public?(classpath, classfile) ⇒ Boolean

Return true if the classfile in the given classpath is public. This is expensive because the jarfile is opened and the classfile is extracted and read.

Returns:

  • (Boolean)


39
40
41
42
43
44
45
46
47
48
# File 'lib/javaclass/classlist/jar_searcher.rb', line 39

def public?(classpath, classfile)
  begin
    header = ClassFile::JavaClassHeader.new(classpath.load_binary(classfile))
  rescue
    puts "error #{$1} for class #{classfile} on #{classpath.to_s}"
    raise
  end
  raise "invalid java class #{classfile}" unless header.magic.valid?
  header.access_flags.accessible?
end