Hello, I'm a passer-by. This is Chapter 31 of spring MVC series.
Today, I have brought you a very important knowledge point: how to deal with cross domain problems in spring MVC. The content of this article is also suitable for spring boot
1. Cross domain access error
When any of the protocol, domain name and port of a request url is different from the current page url, it is cross domain.
For security reasons, the browser prohibits Ajax from calling resources that reside outside the current origin. For example, if an Ajax request is sent from a.com to b.com, the browser console will report a cross domain access error.
As shown below, from http://localhost:63342/ In the site page ttp://localhost:8080/chat21/cors/test2 When you send an ajax request, a red error message appears. The error contains the words access control allow origin. When you see this later, you should see that it is a cross domain problem.
2. Homology definition
Homology policy is an important security policy of the browser. It is used to restrict how the document of one source or its loaded script interacts with another source. It can isolate malicious documents and reduce the attacked media.
If the protocol, host name and port number of the two URLs are the same, the two URLs are homologous. Otherwise, if they are not homologous, cross domain problems will occur in the access of different sources, and the above errors will occur.
The following table shows the and URLs http://store.company.com/dir/page.html Examples of comparing sources:
URL | result | reason |
---|---|---|
http://store.company.com/dir2/other.html | Homology | Only the paths are different |
https://store.company.com/secure.html | Non homologous | Different agreement |
http://store.company.com:81/dir/etc.html | Non homologous | Different port numbers |
http://news.company.com/dir/other.html | Non homologous | Different host names |
That is, when http://store.company.com/dir/page.html In this website https://store.company.com , http://store.company.com:81 and http://news.company.com AXJX requests from three addresses will fail and cross domain errors will be reported. This is the browser's homology strategy, which can only access homologous data.
3. How to solve the cross domain problem?
Cross domain problems need to be solved by CORS. The requester and back-end interfaces need to follow CORS rules to communicate, so as to solve the problem of cross domain access.
Cross origin resource sharing, the full name of CORS, is a system composed of a series of HTTP headers. These HTTP headers determine whether the browser prevents the front-end javascript code from obtaining the response of cross domain requests. Why CORS? This is because the browser has a homologous security policy. When we request resources from another domain in the current domain, the browser will prevent the script from reading its response by default. At this time, CORS has a place to play.
Cross source resource sharing (CORS) is a W3C specification implemented by most browsers, which allows you to flexibly specify what cross domain requests are authorized, rather than using some less secure and powerful policies, such as IFRAME or JSONP.
4. CORS principle
Principle of CORS: to put it simply, some configurations are added to the request header or response header. Through these configurations, cross domain problems can be easily solved.
To understand the principle of CORS in detail, it is recommended to read the following two articles first, and then continue to look down. Otherwise, at last, you know how spring MVC solves it, but you don't know the essential principle.
- CORS communication: http://itsoku.com/article/197
- Browser security policy & CORS: http://itsoku.com/article/198
5. How to solve cross domain problems in spring MVC?
Spring MVC internally provides solutions to cross domain problems. It only needs to make some simple configuration, and the interface can solve cross domain problems without any modification.
The principle of spring MVC to solve cross domain problems is that spring MVC follows the rules of CORS communication to solve cross domain problems, and adds some information required by CORS to the response header.
Spring MVC provides three solutions to cross domain problems. Let's learn about them.
6. Scheme 1: Mark @ CrossOrigin annotation on method or class
- Mark org. On the interface method springframework. web. bind. annotation. CrossOrigin annotation. The @ CrossOrigin annotation is marked on the test1 interface below. This interface supports cross domain access. The @ CrossOrigin annotation contains more detailed configuration, which will not be described in detail here
- You can also mark @ CrossOrigin annotation on the class, then all interfaces in this class will support cross domain access
- You can also mark @ CrossOrigin annotation on classes and methods at the same time. Finally, cross domain access on methods will take the merged configuration
@RestController public class CorsController { @RequestMapping("/cors/test1") @CrossOrigin public List<String> test1() { List<String> result = Arrays.asList("www.itsoku.com", "Spring Master Series", "SpringMVC series", "MySQL series", "High concurrency series"); return result; } }
7. Scheme 2: global configuration
In addition to fine-grained, annotation based configuration, you may need to define some global CORS configurations, which is similar to using filters, but can be declared as Spring MVC combined with fine-grained @ CrossOrigin configuration. By default, all origins and GET, HEAD and POST methods are allowed.
@EnableWebMvc @Configuration public class MvcConfig implements WebMvcConfigurer { @Override public void addCorsMappings(CorsRegistry registry) { //Every time you call registry Addmap can add a cross domain configuration. If multiple configurations are required, you can call registry multiple times addMapping registry.addMapping("/**") .allowedOrigins("*") //Which original domains are released .allowedMethods("PUT", "DELETE","POST", "GET") //Which request methods are released .allowedHeaders("header1", "header2", "header3") //Which original request header information is released .exposedHeaders("header1", "header2") //What header information is exposed .allowCredentials(false) //Send cookies .maxAge(3600); // Add more mappings... } }
8. Scheme 3: interceptor mode CorsFilter
//Handling cross domain filters //1. Add CORS configuration information CorsConfiguration config = new CorsConfiguration(); //Which original domains are released config.addAllowedOrigin("*"); //Send cookies config.setAllowCredentials(false); //Which request methods are released config.addAllowedMethod("*"); //Which original request header information is released config.addAllowedHeader("*"); //What header information is exposed config.addExposedHeader("*"); //2. Add mapping path UrlBasedCorsConfigurationSource corsConfigurationSource = new UrlBasedCorsConfigurationSource(); corsConfigurationSource.registerCorsConfiguration("/**",config);
9. Case code
9.1 complete case code
git address:https://gitee.com/javacode2018/springmvc-series
9.2 interface code: CorsController
There are two interfaces in CorsController. The first interface is marked with @ CrossOrigin annotation, which can solve the problem of cross domain access, while the second method is not marked.
@RestController public class CorsController { @RequestMapping("/cors/test1") @CrossOrigin public List<String> test1() { List<String> result = Arrays.asList("www.itsoku.com", "Spring Master Series", "SpringMVC series", "MySQL series", "High concurrency series"); return result; } @RequestMapping("/cors/test2") public List<String> test2() { List<String> result = Arrays.asList("www.itsoku.com", "Spring Master Series", "SpringMVC series", "MySQL series", "High concurrency series"); return result; } }
9.3. Static page: CORS html
Static page CORS Two buttons are added to HTML. When you click the two buttons, you can access the above two interfaces in ajax cross domain mode respectively. The first button accesses the first interface and the second button accesses the second interface, and then view the effect on the browser console.
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>cors</title> <script type="text/javascript" src="jquery-3.6.0.min.js"></script> <script type="text/javascript"> $(function () { $("#cors-btn1").click(function () { $.ajax({ url: "http://localhost:8080/chat21/cors/test1", success: function (data) { console.log(JSON.stringify(data)); } }); }); $("#cors-btn2").click(function () { $.ajax({ url: "http://localhost:8080/chat21/cors/test2", success: function (data) { console.log(JSON.stringify(data)); } }); }); }) </script> </head> <body> <button id="cors-btn1">Cross domain testing test1</button> <button id="cors-btn2">Cross domain testing test2</button> </body> </html>
9.4 release chat21 cores module to tomcat
9.5. Run the static page CORS html
Select CORS. In idea HTML, and then right-click - > run to run
The operation effect is as follows (it's best to run in chrome browser). The idea supports direct operation of static pages. Please note that the port here is 63342, while the port of tomcat above is 8080. Then press F12 in the browser to open the browser Console, select the Console tab, and click the button to verify the cross domain effect later.
9.6 click the first button to test the cross domain normal request
Take another look at the figure below. For normal cross domain requests, there are several more headers in the response header, mainly because the header at the beginning of access control is related to CORS. The browser determines whether cross domain access is normal according to these response headers. If there are no headers, the browser will refuse to read the response body, and then report an error.
9.7. Click the second button to test the cross domain exception request
10. Summary
Master three ways to solve problems in cross domain MVC
- Annotation method: @ CrossOrigin
- Global configuration method: register CORS configuration in addcorsmapping method of WebMvcConfigurer interface
- Interceptor mode: CorsFilter