I wish to convert json object into x-www-form-urlencoded How can I achieve this in angular 2 final release
export class Compentency {
competencies : number[];
}
postData() {
let array = [1, 2, 3];
this.comp.competencies = array;
let headers = new Headers({ 'Content-Type': 'application/x-www-form-urlencoded' });
let options = new RequestOptions({ headers: headers, method: 'post' });
return this.http.post(this.postUrl, JSON.stringify(this.comp), options)
.map(res => res.json().data.competencies)
.catch(this.handleError);
}
application/x-www-form-urlencoded
Control names and values are escaped. Space characters are replaced by +', and then reserved characters are escaped as described in [RFC1738], section 2.2: Non-alphanumeric characters are replaced by
%HH', a percent sign and two hexadecimal digits representing the ASCII code of the character. Line breaks are represented as "CR LF" pairs (i.e., %0D%0A').
The control names/values are listed in the order they appear in the document. The name is separated from the value by
=' and name/value pairs are separated from each other by `&'.
Therefore you will need to transform your JSON object.
I would simply iterate over the JSON and output:
encodeURIComponent(propertyKey) + "=" + encodeURIComponent(propertyValue) and will combine them using the & sign.
e.g.
var str = [];
for (var key in obj) {
if (obj.hasOwnProperty(key)) {
str.push(encodeURIComponent(key) + "=" + encodeURIComponent(obj[key]))
console.log(key + " -> " + obj[key]);
}
}
return str.join("&");
use querystring,
npm install querystring
var querystring = require('querystring')
var inputJson = {
name: "Asdf",
age: 23
}
console.log(querystring.stringify(inputJson))
This will convert your json into application/x-www-form-urlencoded
Assume have an object named postdata as below:
const postdata = {
'a':1,
'b':2,
'c':3
};
and, you want convert it into x-www-form-urlencoded format, like: a=1&b=2&c=3
with URLSearchParams it's very easy to do it.
const rawData = new URLSearchParams(Object.keys(postdata).map(key=>[key,postdata[key]]));
console.log(rawData.toString());//a=1&b=2&c=3
The non-recursive variant can be expressed as a one-liner with ES6 / TypeScript:
const formEncodedBody = Object.keys(obj).filter(k => obj.hasOwnProperty(k)).map(
k => encodeURIComponent(k) + '=' + encodeURIComponent(obj[k])).join('&');
Note that this algorithm (as the other solution as well) makes some assumptions:
- The properties of the objects are all non-null (but that could be filtered)
- The string representation of each property is exactly what shall be sent (e.g. no special treatment of arrays, booleans as true/false, not as 0/1 or yes/no...)
- No recursion (no property is an object).
private String toFormString(Object t)
{
boolean needConectFlag = false;
StringBuilder result = new StringBuilder();
BeanInfo info;
try
{
info = Introspector.getBeanInfo(t.getClass());
}
catch (IntrospectionException e)
{
throw new HttpMessageConversionException("failed to getBeanInfo", e);
}
PropertyDescriptor[] descriptors = info.getPropertyDescriptors();
for (PropertyDescriptor d : descriptors)
{
Method getMethod = d.getReadMethod();//Read对应get()方法
Object retValue = null;
try
{
retValue = getMethod.invoke(t);
}
catch (IllegalAccessException e)
{
throw new HttpMessageConversionException("failed to invoke,IllegalAccess", e);
}
catch (IllegalArgumentException e)
{
throw new HttpMessageConversionException("failed to invoke,IllegalArgument", e);
}
catch (InvocationTargetException e)
{
throw new HttpMessageConversionException("failed to invoke,InvocationTarget", e);
}
if (retValue != null && !d.getName().equals("class"))
{
if (needConectFlag)
{
result.append("&");
}
result.append(d.getName()).append("=").append(retValue);
needConectFlag = true;
}
}
return result.toString();
}