Class: JavaClass::ClassList::JarSearcher
- 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
-
#skip_inner_classes ⇒ Object
Returns the value of attribute skip_inner_classes.
-
#skip_package_classes ⇒ Object
Returns the value of attribute skip_package_classes.
Instance Method Summary collapse
- #accessible? ⇒ Boolean
-
#add_list_from_classpath(version, classpath, list) ⇒ Object
Compile the class list for the given classpath .
-
#compile_list(version, path, list) ⇒ Object
Compile the class list for the given version of Java.
-
#filter_classes(classes) ⇒ Object
Return the list of classnames of this list of classes .
-
#filters=(filters) ⇒ Object
The given filters will be dropped during searching.
-
#initialize ⇒ JarSearcher
constructor
Create a new searcher.
-
#public?(classpath, classfile) ⇒ Boolean
Return true if the classfile in the given classpath is public.
Constructor Details
#initialize ⇒ JarSearcher
Create a new searcher.
27 28 29 30 31 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 27 def initialize @skip_inner_classes = true @skip_package_classes = false @package_filters = [] end |
Instance Attribute Details
#skip_inner_classes ⇒ Object
Returns the value of attribute skip_inner_classes.
23 24 25 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 23 def skip_inner_classes @skip_inner_classes end |
#skip_package_classes ⇒ Object
Returns the value of attribute skip_package_classes.
24 25 26 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 24 def skip_package_classes @skip_package_classes end |
Instance Method Details
#accessible? ⇒ Boolean
62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 62 def accessible? if @skip_package_classes && !@header.access_flags.accessible? # not public and we only want public false elsif @skip_inner_classes || !@header.attributes.inner_class? # no inner classes have been collected, everything is accessible due its public flag # or this is not an inner class, so everything is OK true # it is an inner class elsif @header.access_flags.synthetic? || @header.attributes.anonymous? # the inner class is anonymous or synthetic, not accessible false elsif !@header.attributes.static_inner_class? # must be static (and not private nor protected) to be accessible false elsif !@skip_package_classes # inner class is public or package access, OK true else # inner class is public, but parent class might be package only public?(@classpath, @header.attributes.outer_class.to_class_file) end end |
#add_list_from_classpath(version, classpath, list) ⇒ Object
Compile the class list for the given classpath . 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.
105 106 107 108 109 110 111 112 113 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 105 def add_list_from_classpath(version, classpath, list) filter_classes(classpath.names).each do |entry| is_public = public?(classpath, entry) next if !accessible? list.add_class(entry, is_public, version) if list yield(entry, is_public, version) if block_given? end end |
#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.
96 97 98 99 100 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 96 def compile_list(version, path, list) cpe = Classpath::AnyClasspath.new(path) add_list_from_classpath(version, cpe, list) 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.
41 42 43 44 45 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 41 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/
.
34 35 36 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 34 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 JAR file is opened and the classfile is extracted and read.
49 50 51 52 53 54 55 56 57 58 59 60 |
# File 'lib/javaclass/classlist/jar_searcher.rb', line 49 def public?(classpath, classfile) # temporal hack, store @classpath and @header @classpath = classpath begin @header = ClassFile::JavaClassHeader.new(classpath.load_binary(classfile)) rescue JavaClass::ClassFile::ClassFormatError => ex ex.add_classname(classfile, classpath.to_s) raise ex end @header.magic.check("invalid java class #{classfile}") @header.access_flags.accessible? end |