1 package org.apache.maven.index.creator;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 import javax.inject.Named;
23 import javax.inject.Singleton;
24 import java.io.File;
25 import java.io.IOException;
26 import java.util.Arrays;
27 import java.util.Collection;
28 import java.util.Enumeration;
29 import java.util.zip.ZipEntry;
30 import java.util.zip.ZipFile;
31
32 import org.apache.lucene.document.Document;
33 import org.apache.maven.index.ArtifactContext;
34 import org.apache.maven.index.ArtifactInfo;
35 import org.apache.maven.index.IndexerField;
36 import org.apache.maven.index.IndexerFieldVersion;
37 import org.apache.maven.index.MAVEN;
38 import org.codehaus.plexus.util.StringUtils;
39
40
41
42
43
44 @Singleton
45 @Named( JarFileContentsIndexCreator.ID )
46 public class JarFileContentsIndexCreator
47 extends AbstractIndexCreator
48 implements LegacyDocumentUpdater
49 {
50 public static final String ID = "jarContent";
51
52 public static final IndexerField FLD_CLASSNAMES = new IndexerField( MAVEN.CLASSNAMES, IndexerFieldVersion.V3,
53 "classnames", "Artifact Classes (tokenized)", IndexerField.ANALYZED_NOT_STORED );
54
55
56
57
58
59
60 public static final IndexerField FLD_CLASSNAMES_KW = new IndexerField( MAVEN.CLASSNAMES, IndexerFieldVersion.V1,
61 "c", "Artifact Classes (tokenized on newlines only)", IndexerField.ANALYZED_STORED );
62
63 public JarFileContentsIndexCreator()
64 {
65 super( ID );
66 }
67
68 public void populateArtifactInfo( final ArtifactContext artifactContext )
69 throws IOException
70 {
71 ArtifactInfo ai = artifactContext.getArtifactInfo();
72
73 File artifactFile = artifactContext.getArtifact();
74
75 if ( artifactFile != null && artifactFile.isFile()
76 && ( artifactFile.getName().endsWith( ".jar" )
77 || artifactFile.getName().endsWith( ".war" )
78 || artifactFile.getName().endsWith( ".zip" ) ) )
79 {
80 updateArtifactInfo( ai, artifactFile );
81 }
82 }
83
84 public void updateDocument( final ArtifactInfo ai, final Document doc )
85 {
86 if ( ai.getClassNames() != null )
87 {
88 doc.add( FLD_CLASSNAMES_KW.toField( ai.getClassNames() ) );
89 doc.add( FLD_CLASSNAMES.toField( ai.getClassNames() ) );
90 }
91 }
92
93 public void updateLegacyDocument( final ArtifactInfo ai, final Document doc )
94 {
95 if ( ai.getClassNames() != null )
96 {
97 String classNames = ai.getClassNames();
98
99
100 if ( classNames.length() > 0 && classNames.charAt( 0 ) == '/' )
101 {
102
103 String[] lines = classNames.split( "\\n" );
104 StringBuilder sb = new StringBuilder();
105 for ( String line : lines )
106 {
107 sb.append( line.substring( 1 ) ).append( '\n' );
108 }
109
110 classNames = sb.toString();
111 }
112
113 doc.add( FLD_CLASSNAMES_KW.toField( classNames ) );
114 }
115 }
116
117 public boolean updateArtifactInfo( final Document doc, final ArtifactInfo artifactInfo )
118 {
119 String names = doc.get( FLD_CLASSNAMES_KW.getKey() );
120
121 if ( names != null )
122 {
123 if ( names.length() == 0 || names.charAt( 0 ) == '/' )
124 {
125 artifactInfo.setClassNames( names );
126 }
127 else
128 {
129
130 String[] lines = names.split( "\\n" );
131 StringBuilder sb = new StringBuilder();
132 for ( String line : lines )
133 {
134 sb.append( '/' ).append( line ).append( '\n' );
135 }
136 artifactInfo.setClassNames( sb.toString() );
137 }
138
139 return true;
140 }
141
142 return false;
143 }
144
145 private void updateArtifactInfo( final ArtifactInfo ai, final File f )
146 throws IOException
147 {
148 if ( f.getName().endsWith( ".jar" ) || f.getName().endsWith( ".zip" ) )
149 {
150 updateArtifactInfo( ai, f, null );
151 }
152 else if ( f.getName().endsWith( ".war" ) )
153 {
154 updateArtifactInfo( ai, f, "WEB-INF/classes/" );
155 }
156 }
157
158 private void updateArtifactInfo( final ArtifactInfo ai, final File f, final String strippedPrefix )
159 throws IOException
160 {
161
162 try ( ZipFile zipFile = new ZipFile( f ) )
163 {
164 final Enumeration<? extends ZipEntry> entries = zipFile.entries();
165
166 final StringBuilder sb = new StringBuilder();
167
168 while ( entries.hasMoreElements() )
169 {
170 String name = entries.nextElement().getName();
171 if ( name.endsWith( ".class" ) )
172 {
173
174
175
176 int i = name.indexOf( "$" );
177
178 if ( i == -1 )
179 {
180 if ( name.charAt( 0 ) != '/' )
181 {
182 sb.append( '/' );
183 }
184
185 if ( StringUtils.isBlank( strippedPrefix ) )
186 {
187
188 sb.append( name, 0, name.length() - 6 ).append( '\n' );
189 }
190 else if ( name.startsWith( strippedPrefix )
191 && ( name.length() > ( strippedPrefix.length() + 6 ) ) )
192 {
193
194 sb.append( name, strippedPrefix.length(), name.length() - 6 ).append( '\n' );
195 }
196 }
197 }
198 }
199
200 final String fieldValue = sb.toString().trim();
201
202 if ( fieldValue.length() != 0 )
203 {
204 ai.setClassNames( fieldValue );
205 }
206 else
207 {
208 ai.setClassNames( null );
209 }
210 }
211 }
212
213 @Override
214 public String toString()
215 {
216 return ID;
217 }
218
219 @Override
220 public Collection<IndexerField> getIndexerFields()
221 {
222 return Arrays.asList( FLD_CLASSNAMES, FLD_CLASSNAMES_KW );
223 }
224 }