Spring Source Code Analysis-interface and abstract class analysis for Resource Access

Source: Internet
Author: User

Spring Source Code Analysis-interface and abstract class analysis for Resource Access
Starting from today, we have taken a step-by-step approach to source code analysis. At the beginning, you must start with something simple. Let's start with Spring, and its Resource abstract interface Resource, the most powerful framework in the development history of Java. I have read a lot of Spring source code analysis. At the beginning, Spring typical modules such as Spring IOC, AOP, and BeanFactory are annoying. These are for the time being. My idea is to analyze what others have not analyzed, or analyze what others have analyzed from different angles. Many programmers who have used Spring for many years may have limited knowledge about resources. After all, accessing resources is generally a matter of building a web engineering framework. But it is also very beneficial to understand it. This interface makes it easier for us to manipulate underlying resources. Because JDK basically controls underlying resources such as java.net. URL, java. io. File, and java. util. Properties. Retrieving resources is based on the absolute path or the relative path of the current class. It is not convenient to obtain resources from the classless path or Web Container context. The Resource interface provides more powerful access to underlying resources. Let's talk a little bit about it. Let's take a look at the Resource class structure before looking at the source code. I. class structure I. Resource interface. The Resouce interface is not a root interface. It inherits a simple parent interface, InputStreamSource, which has only one method to return an input stream: inputStream getInputStream () throws IOException;, directly go to the source code of the Resource interface. The Chinese language is translated according to the English annotations, as shown below: copy the public interface Resource extends InputStreamSource {boolean exists (); // check whether the Resource exists boolean isReadable (); // whether the Resource is readable boolean isOpen (); // whether the handle represented by the resource is opened by a stream URL getURL () throws IOException; // The handle URI of the returned resource URL getURI () Throws IOException; // return the resource URI handle File getFile () throws IOException; // return the resource's File handle long contentLength () throws IOException; // The length of the Resource content long lastModified () throws IOException; // The last modification time of the Resource: Resource createRelative (String relativePath) throws IOException; // create a new resource String getFilename () based on the relative path of the resource; // The resource file name String getDescription (); // Resource Description}. Copy the Code. There is nothing to say. Continue! 2. abstract class AbstractResource for any interface, this direct abstract class is the top priority, which concentrates most of the public implementations of the interface. The translation is as follows: copy the code public abstract class into actresource implements Resource {public boolean exists () {// check whether the file exists. If an exception occurs during the process (because SecurityManager is called to determine whether the file exists ), close the corresponding stream try {return getFile (). exists ();} catch (IOException ex) {try {InputStream is = getInputStream (); // The getInputStream () method will be overwritten by the quilt class, is. close (); return true;} catch (Throwable isEx) {return false ;}} public boolean isReadable () {// return true directly, readable ret Urn true;} public boolean isOpen () {// directly return false, not open return false;} public URL getURL () throws IOException {// Leave It to The subclass to override throw new FileNotFoundException (getDescription () + "cannot be resolved to URL");} public URI getURI () throws IOException {// return url URL url = getURL (); try {return ResourceUtils. toURI (url); // format the url and return} catch (URISyntaxException ex) {throw new NestedIOException ("Invalid U RI ["+ url +"] ", ex) ;}} public File getFile () throws IOException {// rewrite throw new FileNotFoundException (getDescription () for the subclass () + "cannot be resolved to absolute file path");} // The length of the resource content is actually the length of the resource byte, which can be determined by reading it all. This method occupies resources! Public long contentLength () throws IOException {InputStream is = this. getInputStream (); Assert. state (is! = Null, "resource input stream must not be null"); // asserted try {long size = 0; byte [] buf = new byte [255]; int read; while (read = is. read (buf ))! =-1) {size + = read;} return size;} finally {try {is. close () ;}catch (IOException ex) {}} public long lastModified () throws IOException {// return the last modification time of the resource long lastModified = getFileForLastModifiedCheck (). lastModified (); if (lastModified = 0L) {throw new FileNotFoundException (getDescription () + "cannot be resolved in the file system for resolving its last-modified timestamp ");} return l AstModified;} // This is a method not available in the Resource interface. The comment indicates "Return file, check the timestamp", and the subclass must be rewritten... protected File getFileForLastModifiedCheck () throws IOException {return getFile ();} public Resource createRelative (String relativePath) throws IOException {// Leave It To The subclass to override throw new FileNotFoundException ("Cannot create a relative resource for" + getDescription ();} public String getFilename () {// null is returned by default (assuming the resource does not have a file name), unless the subclass overwrites return null ;}@ Override public String toString () {// toString returned file description return getDescription () ;}@ Override public boolean equals (Object obj) {// equals compares the two Resource descriptions. return (obj = this | (obj instanceof Resource & (Resource) obj ). getDescription (). equals (getDescription ();} @ Override public int hashCode () {// return the HashCode return getDescription () of the Resource description (). hashCode () ;}} copy the code. Conclusion: 1. added a method, protected File ge. TFileForLastModifiedCheck () throws IOException requires subclass implementation. If the subclass is not implemented, the resource file is directly returned. The specific function of this method is described later in the implementation class. 2. The contentLength () method is a heavyweight method. It reads all resources to determine the number of bytes of the resource. 255 bytes of buffer array to read. Subclasses are generally overwritten. (Adjust the buffer array size ?) 3. getDescription () is the only interface method that is not implemented in this abstract class. It is left to the subclass for implementation. The default equals () and hashCode () of the resource file are determined by this method. 4. The unique method getInputStream () of InputStreamSource is not implemented and left to the subclass. 3. The sub-interfaces ContextResource and WritableResource of Resource inherit from Resource and have all the methods of Resource. The ContextResource interface adds a method: String getPathWithinContext (); // return the path in the context. This method enables its implementation class to return the current context path. The WritableResource interface adds two methods: boolean isWritable (); // whether OutputStream getOutputStream () throws IOException can be written; // return the resource write stream. This method enables its implementation class to write resources. PS: the framework is like this. It is not difficult and the design model is not used much. But there is a kind of feeling of no work, no front, because the use of code is really very concise. By analyzing the source code, you can also read your English documents to a large extent. Mutual encouragement.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.