1

I am trying to run a Spring Boot application locally and I have some issues making an AJAX request back to the app. Chrome gives me the following error (which is actually from jquery):

Failed to load localhost:8080/api/input: Cross origin requests are only supported for protocol schemes: http, data, chrome, chrome-extension, https.

I am trying to make a POST request that will be handled by the following method. This actually works with Postman.

@RequestMapping(value = "/api/input", method = RequestMethod.POST)
public @ResponseBody UserInputModel getUserInput(@RequestBody UserInputModel input)
{
    input.setMessage("bye");

    return input;
}

Here's the script that's making the request:

$(document).ready(function () {
$('#submitInput').click(function () {

    // Only send the message to the server if the user typed something
    var userMessage = {
        message: $('#userInput').val()
    };

    console.log(userMessage);

    if (userMessage.message) {
        console.log("Sending request");
        $.ajax({
            url: "localhost:8080/api/input",
            dataType: "json",
            contentType: "application/json; charset=UTF-8",
            data: JSON.stringify(userMessage),
            type: 'POST',
            success: function() {
                console.log("yay");
            },
            error: function(err) {
                console.log(err);
            }
        });
    } else {
        console.log("Empty input, no request sent");
    }
});

console.log("Loaded testScript.js");
});

So here's what's working. I have another controller that returns an html page (which also loads my script). This does work in Chrome, I get my page with the textbox and button and the script is indeed loaded. The problem is that the request from the script back to the app is not working.

Here's the pom.xml:

<?xml version="1.0" encoding="UTF-8"?>

http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0

<groupId>my.group</groupId>
<artifactId>appname</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>

<name>appname</name>
<description>Demo project for Spring Boot</description>

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>1.5.8.RELEASE</version>
</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>mysql</groupId>
        <artifactId>mysql-connector-java</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>
            <configuration>
                <addResources>true</addResources>
            </configuration>
        </plugin>
    </plugins>
</build>

Xzenon
  • 1,193
  • 2
  • 15
  • 37
  • 1
    try to use url: "/api/input" without the full path – vratojr Nov 30 '17 at 13:47
  • @vratojr You deserve a big fat kiss. But why exactly is this working? – Xzenon Nov 30 '17 at 13:49
  • @Xzenon It only works if the API is on the same host as the client you are sending the http request from. Read up on CORS. – szab.kel Nov 30 '17 at 13:53
  • I'm not sure :) It's something I've experienced, I think that putting the full address is interpretated by the brower as the will to do a cross origin request. If you don't specify the address it means that you are using the GOOD one and you are not trying to do bad things. – vratojr Nov 30 '17 at 13:57
  • is the web app delivered by the spring boot appliction? If not, can you make sure, that it is always coming from the same host as the api server? If not you have to enable CORS in your spring boot app. check https://spring.io/guides/gs/rest-service-cors/ for that – P.J.Meisch Nov 30 '17 at 14:55
  • @P.J.Meisch The web app should be delivered by the spring boot app. – Xzenon Nov 30 '17 at 14:57
  • then @vratojr 's answer is enough ;-) – P.J.Meisch Nov 30 '17 at 15:06

1 Answers1

3

You can use JSONP: https://dev.socrata.com/docs/cors-and-jsonp.html

Or you can specify an explicit config in Spring boot:

@Configuration
public class RestConfig {
    @Bean
    public CorsFilter corsFilter() {
        UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
        CorsConfiguration config = new CorsConfiguration();
        config.setAllowCredentials(true);
        config.addAllowedOrigin("*");
        config.addAllowedHeader("*");
        config.addAllowedMethod("OPTIONS");
        config.addAllowedMethod("GET");
        config.addAllowedMethod("POST");
        config.addAllowedMethod("PUT");
        config.addAllowedMethod("DELETE");
        source.registerCorsConfiguration("/**", config);
        return new CorsFilter(source);
    }
}

Check out: How to configure CORS in a Spring Boot + Spring Security application?

szab.kel
  • 2,356
  • 5
  • 40
  • 74