spring boot ajax跨域的两种方式
前言 java语言在多数时,会作为一个后端语言,为前端的php,node.js等提供API接口。前端通过ajax请求去调用java的API服务。今天以node.js为例,介绍两种跨域方式:CrossOrigin和反向代理。 一、准备工作 pom.xml: <?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.example</groupId> <artifactId>spring-boot-15</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>jar</packaging> <name>spring-boot-15</name> <description>Demo project for Spring Boot</description> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>1.5.3.RELEASE</version> <relativePath/> <!-- lookup parent from repository --> </parent> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding> <java.version>1.8</java.version> </properties> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> <scope>runtime</scope> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project> pom.xml App.java package com.example; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication @SpringBootApplication public class App { public static void main(String[] args) { SpringApplication.run(App.class,args); } } User.java package com.example; public class User { public int id; public String name; public int age; } MainController.java: package com.example; import java.util.ArrayList; import java.util.List; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RestController; /** * * */ @RestController public class MainController { @GetMapping("findAllUser") public List<User> findAllUser() { List<User> list = new ArrayList<>(); for (int i = 0; i < 20; i++) { User user = new User(); list.add(user); user.id = i; user.name = "name_" + i; user.age = 20 + i; } return list; } } 项目结构如下图所示: 访问http://localhost:8080/findAllUser 使用HBuilder创建node.js express项目: 选择ejs模板引擎: index.ejs文件代码如下: <!DOCTYPE html> <html> <head> <title> <%= title %> </title> <link rel='stylesheet' href='/stylesheets/style.css' /> <script src="//cdn.bootcss.com/angular.js/1.5.6/angular.min.js"></script> <script type="text/javascript"> var app = angular.module('app',[]); app.controller('MainController',function($rootScope,$scope,$http) { $http({ method: 'GET',url: 'http://localhost:8080/findAllUser' }).then(function successCallback(r) { $scope.rows = r.data; }); }); </script> </head> <body ng-app="app" ng-controller="MainController"> <h1><%= title %></h1> <p>Welcome to <%= title %> </p> <br /> <table> <tr ng-repeat="row in rows"> <td>{{row.id}}</td> <td>{{row.name}}</td> <td>{{row.age}}</td> </tr> </table> </body> </html> 通过angular.js的http方法调用api请求 右键运行项目: 运行效果: 发现调用ajax请求时跨域失败。 二、spring boot后台设置允许跨域 这时,修改MainController类,在方法前加@CrossOrigin注解: /** * * */ @RestController public class MainController { @CrossOrigin(origins = "http://localhost:3000") @GetMapping("findAllUser") public List<User> findAllUser() { List<User> list = new ArrayList<>(); for (int i = 0; i < 20; i++) { User user = new User(); list.add(user); user.id = i; user.name = "name_" + i; user.age = 20 + i; } return list; } } 这是声明findAllUser方法允许跨域, 也可以修改App.java,来实现全局跨域: package com.example; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.context.annotation.Bean; import org.springframework.web.servlet.config.annotation.CorsRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter; @SpringBootApplication public class App { public static void main(String[] args) { SpringApplication.run(App.class,args); } @Bean public WebMvcConfigurer corsConfigurer() { return new WebMvcConfigurerAdapter() { @Override public void addCorsMappings(CorsRegistry registry) { registry.addMapping("/**").allowedOrigins("http://localhost:3000"); } }; } } registry.addMapping("/**"):为根目录的全部请求,也可以设置为"/user/**",这意味着是user目录下的所有请求。 在访问http://localhost:3000,效果如下: 三、通过node.js的方向代理实现跨域 node.js提供了一些反向代理的中间件,能轻而易举的实现跨域,而不需要spring boot做任何设置。 安装express-http-proxy中间件 npm install --save-dev express-http-proxy 修改app.js文件,使其支持反向代理: var proxy = require('express-http-proxy'); var apiProxy = proxy('http://localhost:8080',{}); app.use('/api',apiProxy); 以“/api”开头的请求转发为spring boot的API服务。 完整代码如下: /** * Module dependencies. */ var express = require('express'),routes = require('./routes'),user = require('./routes/user'),http = require('http'),path = require('path'); var app = express(); // all environments app.set('port',process.env.PORT || 3000); app.set('views',__dirname + '/views'); app.set('view engine','ejs'); app.use(express.favicon()); app.use(express.logger('dev')); app.use(express.bodyParser()); app.use(express.methodOverride()); app.use(app.router); app.use(express.static(path.join(__dirname,'public'))); // development only if ('development' == app.get('env')) { app.use(express.errorHandler()); } var proxy = require('express-http-proxy'); var apiProxy = proxy('http://localhost:8080',apiProxy); app.get('/',routes.index); app.get('/users',user.list); http.createServer(app).listen(app.get('port'),function(){ console.log('Express server listening on port ' + app.get('port')); }); 修改index.ejs文件: var app = angular.module('app',url: '/api/findAllUser' }).then(function successCallback(r) { $scope.rows = r.data; }); }); (编辑:安卓应用网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |