Project

General

Profile

Download (7.15 KB) Statistics
| Branch: | Tag: | Revision:
1
// $Id$
2
/**
3
* Copyright (C) 2007 EDIT
4
* European Distributed Institute of Taxonomy
5
* http://www.e-taxonomy.eu
6
*
7
* The contents of this file are subject to the Mozilla Public License Version 1.1
8
* See LICENSE.TXT at the top of this package for the full license terms.
9
*/
10
package eu.etaxonomy.cdm.remote.view;
11

    
12
import java.io.PrintWriter;
13
import java.util.Collection;
14
import java.util.Map;
15

    
16
import javax.servlet.http.HttpServletRequest;
17
import javax.servlet.http.HttpServletResponse;
18

    
19
import net.sf.json.JSON;
20
import net.sf.json.JSONArray;
21
import net.sf.json.JSONObject;
22
import net.sf.json.JsonConfig;
23
import net.sf.json.xml.XMLSerializer;
24

    
25
import org.apache.log4j.Logger;
26
import org.springframework.web.servlet.View;
27

    
28
import eu.etaxonomy.cdm.remote.config.DataSourceProperties;
29

    
30

    
31
public class JsonView extends BaseView implements View{
32

    
33
    public static final Logger logger = Logger.getLogger(JsonView.class);
34

    
35
    private JsonConfig jsonConfig;
36

    
37
    private DataSourceProperties dataSourceProperties;
38

    
39
    public DataSourceProperties getDataSourceProperties() {
40
        return dataSourceProperties;
41
    }
42

    
43
    public void setDataSourceProperties(DataSourceProperties dataSourceProperties) {
44
        this.dataSourceProperties = dataSourceProperties;
45
    }
46

    
47
    public enum Type{
48
        JSON("application/json"),
49
        XML("application/xml");
50

    
51
        private final String contentType;
52

    
53
        Type(String contentType){
54
            this.contentType = contentType;
55
        }
56

    
57
        public String getContentType(){
58
            return contentType;
59
        }
60
    }
61

    
62
    private Type type = Type.JSON;
63

    
64
    private String xsl = null;
65

    
66
    public void setXsl(String xsl) {
67
        this.xsl = xsl;
68
    }
69

    
70
    public String getXsl() {
71
        return xsl;
72
    }
73

    
74
    public Type getType() {
75
        return type;
76
    }
77

    
78
    /**
79
     * Default is Type.JSON
80
     * @param type
81
     */
82
    public void setType(Type type) {
83
        this.type = type;
84
    }
85

    
86
    public void setJsonConfig(JsonConfig jsonConfig) {
87
        this.jsonConfig = jsonConfig;
88
    }
89

    
90
    /*
91
     * (non-Javadoc)
92
     * @see org.springframework.web.servlet.View#getContentType()
93
     */
94
    @Override
95
    public String getContentType() {
96
        return type.getContentType();
97
    }
98

    
99
    /* (non-Javadoc)
100
     * @see eu.etaxonomy.cdm.remote.view.BaseView#render(java.lang.Object, java.io.PrintWriter, java.lang.String, java.lang.String)
101
     */
102
    @Override
103
    public void render(Object entity, PrintWriter writer, String jsonpCallback, HttpServletRequest request, HttpServletResponse response) throws Exception {
104

    
105
        String contextPath = null;
106

    
107
        if (request != null)
108
        	{
109
        	contextPath = request.getContextPath();
110
        	}
111

    
112
        if(jsonConfig == null){
113
            logger.error("The jsonConfig must not be null. It must be set in the applicationContext.");
114
        }
115

    
116
        // option to skip json processing for debugging purposes, see #4925
117
        if(System.getProperty("SkipJSON") == null) {
118

    
119
        // create JSON Object
120

    
121
//        long start = System.currentTimeMillis();
122
        boolean isCollectionType = false;
123
        JSON jsonObj;
124
        if (entity == null){
125
          jsonObj = JSONObject.fromObject("{}");
126
        } else if(Collection.class.isAssignableFrom(entity.getClass())){
127
            isCollectionType = true;
128
            jsonObj = JSONArray.fromObject(entity, jsonConfig);
129
        }else if(entity instanceof String){
130
            jsonObj = JSONObject.fromObject("{\"String\":\""+entity.toString().replace("\"", "\\\"")+"\"}");
131
        } else if(entity instanceof Integer){
132
            jsonObj = JSONObject.fromObject("{\"Integer\":"+((Integer)entity).intValue()+"}");
133
        } else if(entity instanceof Boolean){
134
            jsonObj = JSONObject.fromObject("{\"Boolean\":"+((Boolean)entity).toString()+"}");
135
        } else {
136
            jsonObj = JSONObject.fromObject(entity, jsonConfig);
137
        }
138
//        System.err.println("create JSON Object " + (System.currentTimeMillis() - start));
139

    
140
        if(type.equals(Type.XML)){
141
            XMLSerializer xmlSerializer = new XMLSerializer();
142
            if(isCollectionType){
143
                xmlSerializer.setArrayName(entity.getClass().getSimpleName());
144
                Class elementType = Object.class;
145
                Collection c = (Collection)entity;
146
                if(c.size() > 0){
147
                    elementType = c.iterator().next().getClass();
148
                }
149
                xmlSerializer.setObjectName(elementType.getSimpleName());
150
            } else if(entity != null){
151
                xmlSerializer.setObjectName(entity.getClass().getSimpleName());
152
            }
153
            String xml = xmlSerializer.write( jsonObj );
154
            if(type.equals(Type.XML) && xsl != null){
155

    
156
                if(contextPath == null){
157
                    contextPath = "";
158
                }
159
                String basepath = dataSourceProperties.getXslBasePath(contextPath + "/xsl");
160
                String replace = "\r\n<?xml-stylesheet type=\"text/xsl\" href=\"" + basepath + "/" + xsl + "\"?>\r\n";
161
                xml = xml.replaceFirst("\r\n", replace);
162
            }
163
            writer.append(xml);
164
        } else {
165
            // assuming json
166
            if(jsonpCallback != null){
167
                writer.append(jsonpCallback).append("(").append(jsonObj.toString()).append(")");
168
            } else {
169
                writer.append(jsonObj.toString());
170
            }
171
        }
172
        //TODO resp.setContentType(type);
173

    
174
        } else {
175
            writer.append("SkipJSON mode detected, this is for debugging only! Please contact the adminitrator.");
176
            // END SkipJSON
177
        }
178
        writer.flush();
179
    }
180

    
181
    /*
182
     * (non-Javadoc)
183
     * @see org.springframework.web.servlet.View#render(java.util.Map, javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
184
     */
185
    @Override
186
    public void render(Map model, HttpServletRequest request, HttpServletResponse response) throws Exception {
187

    
188
        // Retrieve data from model
189
        Object entity = getResponseData(model);
190

    
191
        // set content type
192
        response.setContentType(type.getContentType());
193

    
194
        PrintWriter writer = response.getWriter();
195

    
196
        // read jsonp parameter from query string
197
        String jsonpCallback = extractJsonpCallback(request);
198

    
199
        // render
200
        render(entity, writer, jsonpCallback, request, response);
201
    }
202

    
203
    /**
204
     * @param request
205
     * @return
206
     */
207
    private String extractJsonpCallback(HttpServletRequest request) {
208
        String jsonpCallback= null;
209
        String queryString = request.getQueryString();
210
        if(queryString != null){
211
            String[] tokens = request.getQueryString().split("&", 0);
212
            String jsonpParamName = "callback";
213
            for (int i = 0; i < tokens.length; i++) {
214
                if(tokens[i].startsWith(jsonpParamName)){
215
                    jsonpCallback = tokens[i].substring(jsonpParamName.length() + 1);
216
                    break;
217
                }
218
            }
219
        }
220
        return jsonpCallback;
221
    }
222
}
(5-5/10)