PacificNW_Lover
PacificNW_Lover

Reputation: 5384

Returned Jackson based JSON is adding extra slashes in payload

Am using Java 1.7, RestEasy, and codehaus version of Jackson (for JSON parsing)...

Have a standard Java POJO DTO which populates a directory path (as a String) based on a Windows 7 filesystem:

import org.codehaus.jackson.annotate.JsonProperty;

public class BackupDirDTO implements Serializable {

    private static final long serialVersionUID = 1L;

    @JsonProperty("id")
    private Long id;

    @JsonProperty("backup-dir")
    private String backupDir;

    // Getters & Setters
}

This is the layer which my business logic occurs... It gets the value from an entity from a database and sets the property in the DTO:

public class DirectoryRepository {

    public BackupDirDTO getDirectoryById(Long id) throws Exception {
        DirectoryEntity entity = directoryRespository.getEntityById(id);
        BackupDirDTO dto = new BackupDirDTO();
        log.debug("Entity.getBackupDir: " + enity.getBackupDirectory());
        dto.setBackupDir(entity.getBackupDirectory());
        log.debug("dto.getBackupDirectory: " + dto.getBackupDir());
        return dto;
    }
}

From my log.debug() calls it looks like this (which is the correct String that I want):

Entity.getBackupDir: "\\my-network-folder\backupDir"
dto.getBackupDirectory: \\my-network-folder\backupDir"

Here's the RESTful Web Service call:

public class DirectoryResource {

    private DirectoryRepository repository;

    @GET
    @Path("/directories/{id}")
    @Produces(MediaType.APPLICATION_JSON)
    public BackupDirDTO getDirectoryById(@PathParam("id") Long id) {
        BackupDirDTO dto = new BackupDirDTO();
        try {
            dto = repository.getDirectoryById(id);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return dto;
    }
}

The actual JSON payload generated from the RESTful Web Service call looks like this:

{"id": 1, "backup-dir": "\\\\my-network-folder\\backupDir"}

Why is it adding an extra slashes?

My pom.xml

<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-jackson-provider</artifactId>
    <scope>provided</scope>
</dependency>

<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-jackson-provider</artifactId>
    <scope>provided</scope>
</dependency>

<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-jaxrs</artifactId>
    <scope>provided</scope>
</dependency>

<dependency>
    <groupId>org.jboss.spec.javax.ws.rs</groupId>
    <artifactId>jboss-jaxrs-api_1.1_spec</artifactId>
    <scope>provided</scope>
</dependency>

<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-jaxb-provider</artifactId>
    <scope>provided</scope>
</dependency>

<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-jdk-http</artifactId>
    <version>2.3.10.Final</version>
    <scope>test</scope>
</dependency>

<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-client</artifactId>
    <version>3.0.10.Final</version>
    <scope>test</scope>
</dependency>

<dependency>
    <groupId>org.jboss.spec.javax.servlet</groupId>
    <artifactId>jboss-servlet-api_3.0_spec</artifactId>
    <scope>provided</scope>
</dependency>

Tried using the Apache Commons library like this (inside the DirectoryRepository.getDirectoryById(Long id) method):

dto.setBackupDir(FilenameUtils.separatorsToUnix(entity.getBackupDirectory()));
dto.setBackupDir(FilenameUtils.separatorsToSystem(entity.getBackDirectory()));
dto.setBackupDir(FilenameUtils.separatorsToWindows(entity.getBackDirectory()));

The only one that doesn't include the extra slashes is (but I need the one for the Windows convention):

FilenameUtils.separatorsToUnix();

Even tried using @JSonRawValue inside my actual web service class:

@JsonRawValue
@JsonProperty("backup-dir")
private String backupDir;

This actually broke a lot of things...

Are the newly added slashes a result in the Web Services layer or Repository layer?

How can I make it more Windows specific?

What I want my JSON payload to look like is this:

{"id": 1, "backup-dir": "\\my-network-folder\backupDir"}

Thank you for taking the time to read this...

Upvotes: 0

Views: 2835

Answers (2)

Cary Young
Cary Young

Reputation: 85

Why is it adding an extra slashes?

You're getting the double backslashes because in JSON, the backslash is an escape character.

What I want my JSON payload to look like is this:

{"id": 1, "backup-dir": "\my-network-folder\backupDir"}

that is not valid JSON. Instead, when the caller of the endpoint deserializes your payload, they will need to parse the escaped backslash correctly. In order to transmit a backslash within JSON, it must be escaped. It just happens that the escape character is also a backslash.

Upvotes: 0

Andremoniy
Andremoniy

Reputation: 34920

Backslash \ is special character in JSON format and it should be escaped.

enter image description here

Otherwise in your example "\\my-network-folder\backupDir" \\ will be interpreted as single reverse solidus and \b as backspace. So Jackson is doing everything correctly, do not try to fix it.

Upvotes: 7

Related Questions