File: TldResourcePath.java

package info (click to toggle)
tomcat9 9.0.70-2
  • links: PTS, VCS
  • area: main
  • in suites: bookworm
  • size: 43,208 kB
  • sloc: java: 358,255; xml: 63,839; jsp: 4,528; sh: 1,204; perl: 315; makefile: 18
file content (171 lines) | stat: -rw-r--r-- 5,830 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
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
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.apache.tomcat.util.descriptor.tld;

import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.util.Objects;

import org.apache.tomcat.Jar;
import org.apache.tomcat.util.scan.JarFactory;
import org.apache.tomcat.util.scan.ReferenceCountedJar;

/**
 * A TLD Resource Path as defined in JSP 7.3.2.
 * <p>
 * This encapsulates references to Tag Library Descriptors that can be located
 * in different places:
 * <ul>
 * <li>As resources within an application</li>
 * <li>As entries in JAR files included in the application</li>
 * <li>As resources provided by the container</li>
 * </ul>
 * When configuring a mapping from a well-known URI to a TLD, a user is allowed
 * to specify just the name of a JAR file that implicitly contains a TLD in
 * <code>META-INF/taglib.tld</code>. Such a mapping must be explicitly converted
 * to a URL and entryName when using this implementation.
 */
public class TldResourcePath {
    private final URL url;
    private final String webappPath;
    private final String entryName;

    /**
     * Constructor identifying a TLD resource directly.
     *
     * @param url        the location of the TLD
     * @param webappPath the web application path, if any, of the TLD
     */
    public TldResourcePath(URL url, String webappPath) {
        this(url, webappPath, null);
    }

    /**
     * Constructor identifying a TLD packaged within a JAR file.
     *
     * @param url        the location of the JAR
     * @param webappPath the web application path, if any, of the JAR
     * @param entryName  the name of the entry in the JAR
     */
    public TldResourcePath(URL url, String webappPath, String entryName) {
        this.url = url;
        this.webappPath = webappPath;
        this.entryName = entryName;
    }

    /**
     * Returns the URL of the TLD or of the JAR containing the TLD.
     *
     * @return the URL of the TLD
     */
    public URL getUrl() {
        return url;
    }

    /**
     * Returns the path within the web application, if any, that the resource
     * returned by {@link #getUrl()} was obtained from.
     *
     * @return the web application path or @null if the the resource is not
     *         located within a web application
     */
    public String getWebappPath() {
        return webappPath;
    }

    /**
     * Returns the name of the JAR entry that contains the TLD.
     * May be null to indicate the URL refers directly to the TLD itself.
     *
     * @return the name of the JAR entry that contains the TLD
     */
    public String getEntryName() {
        return entryName;
    }

    /**
     * Return the external form of the URL representing this TLD.
     * This can be used as a canonical location for the TLD itself, for example,
     * as the systemId to use when parsing its XML.
     *
     * @return the external form of the URL representing this TLD
     */
    public String toExternalForm() {
        if (entryName == null) {
            return url.toExternalForm();
        } else {
            return "jar:" + url.toExternalForm() + "!/" + entryName;
        }
    }

    /**
     * Opens a stream to access the TLD.
     *
     * @return a stream containing the TLD content
     * @throws IOException if there was a problem opening the stream
     */
    public InputStream openStream() throws IOException {
        if (entryName == null) {
            return url.openStream();
        } else {
            URL entryUrl = JarFactory.getJarEntryURL(url, entryName);
            return entryUrl.openStream();
        }
    }

    public Jar openJar() throws IOException {
        if (entryName == null) {
            return null;
        } else {
            // Bug 62976
            // Jar files containing tags are typically opened during initial
            // compilation and then closed when compilation is complete. The
            // reference counting wrapper is used because, when background
            // compilation is enabled, the Jar will need to be accessed (to
            // check for modifications) after it has been closed at the end
            // of the compilation stage.
            // Using a reference counted Jar enables the Jar to be re-opened,
            // used and then closed again rather than triggering an ISE.
            return new ReferenceCountedJar(url);
        }
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) {
            return true;
        }
        if (o == null || getClass() != o.getClass()) {
            return false;
        }

        TldResourcePath other = (TldResourcePath) o;

        return url.equals(other.url) &&
                Objects.equals(webappPath, other.webappPath) &&
                Objects.equals(entryName, other.entryName);
    }

    @Override
    public int hashCode() {
        int result = url.hashCode();
        result = result * 31 + Objects.hashCode(webappPath);
        result = result * 31 + Objects.hashCode(entryName);
        return result;
    }
}