I am using a maeven dependecie that maintain the order of key values of java, but the prblem is that display a double bracket when i m usin a jsonArray. Can someone tell me where my mistake is.
mssgErreurResult() is a method that return an Arraylist that contains all my error messages. Just imagine that Errors ... in the JsonFile is the return of that method
What i get :
{
"complet": false,
"erreurs": [
[
"Errors ..."
]
]
}
What i want:
{
"complet": false,
"erreurs":[
"Errors ..."
]
}
The method i used:
public void ecrireFichierJSon(String fichierSortie) throws
FichierJsonInvalideException, org.codehaus.jettison.json.JSONException {
org.codehaus.jettison.json.JSONObject completOrNot = new org.codehaus.jettison.json.JSONObject();
completOrNot.put("complet", mssgErreurResult().size() <= 0);
org.codehaus.jettison.json.JSONArray messagesErreur = new org.codehaus.jettison.json.JSONArray();
messagesErreur.put(mssgErreurResult());
completOrNot.put("erreurs", messagesErreur);
try {
Files.write(Paths.get(fichierSortie), completOrNot.toString().getBytes());
} catch (IOException e) {
throw new FichierJsonInvalideException(e.toString());
}
}
It is added with extra [ ... ] by org.codehaus.jettison.json.JSONArray messagesErreur, try to remove it and use the following instead
completOrNot.put("erreurs", mssgErreurResult());
Related
We have a collection of scrips :
{
"_id" : ObjectId("xxxxxxx"),
"scrip" : "3647"
}
{
"_id" : ObjectId("yyyyyy"),
"scrip" : "5647"
}
...
We are simply attempting to return the scrip numerals as an array of string using java driver 3.7
ArrayList<Document> scriplist = scrips.aggregate(Arrays.asList(
Aggregates.group(
Accumulators.push("scripids",
new Document("_id", "$id").
append("scripids", "$scripid"))
)
)).into(new ArrayList<>());
System.out.println(scriplist.toString());
Expected output is ['3647','5647'].
However,we get a 'Can't find a codec for class com.mongodb.client.model.BsonField.' exception.
How is this to be done?
The following query can get us the expected output:
db.scrips.distinct("scrip");
Output:
["3647","5647"]
Equivalent code in Java:
DistinctIterable<String> iterable = scrips.distinct("scrip", String.class);
List<String> scrips = new ArrayList<>();
Block<String> block = scrip -> scrips.add(scrip);
iterable.forEach(block);
The 'scrips' set would hold the distinct scrips.
Some other ways to do the same:
db.scrips.aggregate([
{
$group:{
"_id":"$scrip"
}
},
{
$group:{
"_id":null,
"scrips":{
$push:"$_id"
}
}
},
{
$project:{
"_id":0
}
}
])
Java code:
scrips.aggregate(
Arrays.asList(Aggregates.group("$scrip"), Aggregates.group(null, Accumulators.push("scrips", "$_id")),
Aggregates.project(Projections.exclude("_id"))));
db.scrips.aggregate([
{
$group:{
"_id":null,
"scrips":{
$addToSet:"$scrip"
}
}
},
{
$project:{
"_id":0
}
}
])
Java code:
scrips.aggregate(Arrays.asList(Aggregates.group(null, Accumulators.addToSet("scrips", "$_id")),
Aggregates.project(Projections.exclude("_id"))));
I have a file in JSON format. Gson parser crashes when it encounters a blank in it, as in State = "West Virginia", but it can parse "West-Virginia" where the blank character is replaced. I am using BufferedReader in Java.
But if I pass the same string hard-coded, the parser works.
import java.io.* ;
import com.google.gson.*;
public class gson_test {
public static void main(String[] args) throws FileNotFoundException {
// TODO Auto-generated method stub
BufferedReader br2 = null ;
String jsonStr = "[{month = august, weather:clear}, [333] , {addr : {place = {city = city_name, county : its_name}, state = \"West Virginia\" } } ]" ;
// System.out.printf("json-str : %s \n", jsonStr);
GsonParseStr(jsonStr, (JsonElement) null );
try {
String file2read_json = "c:\\enter\\filename\\here";
br2 = new BufferedReader(new FileReader(file2read_json));
// https://sites.google.com/site/gson/gson-user-guide#TOC-Array-Examples
Gson gson = new GsonBuilder().setPrettyPrinting().serializeNulls().create();
Object obj2 = gson.fromJson(br2, Object.class); // parses json-str into an object
GsonParseStr(obj2.toString(), (JsonElement) null );
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if (br2 != null) {
br2.close();
}
} catch (IOException ex) {
ex.printStackTrace();
}
}
}
static void GsonParseStr(String jsonStr, JsonElement elem) {
JsonParser parser2 = new JsonParser();
elem = parser2.parse(jsonStr); // this stmt crashes for the blank char
System.out.printf("parse str : %s \n", jsonStr);
}
}
My file's content is:
[{month = august, weather:clear}, [333] , {addr : {place = {city = city_name, county : its_name}, state = "West.Virginia" } } ]
If I change "West.Virginia" to "West Virginia" the program crashes.
The file should get parsed the same way as 'file-contents in the form of raw string'.
PS : As suggested by JPinzon, I need quotes around (West Virginia) in the file, which I did have. But they have to be further escaped. Thus : (State: "West Virginia") won't do; it should be (State: "\"West Virginia\""). Optionally, the key 'State' can have double-quotes around it, but that is optional.
Try fixing your JSON to this:
[{"month":"august", "weather":"clear"}, [333], {"addr":{"place":{"city":"city_name", "county":"its_name"}, "state":"West Virginia"}}]
... or nicely formatted:
[
{
"month":"august",
"weather":"clear"
},
[
333
],
{
"addr":{
"place":{
"city":"city_name",
"county":"its_name"
},
"state":"West Virginia"
}
}
]
If you debug, you will see that the string obj2.toString() doesn't contain quotes around "West Virginia" because the gson.fromJson(br2, Object.class) has removed them while parsing. That's why it crashes.
To avoid this error you can try adding escaped quotes in your file like this state = "\"West Virginia\""
I'm trying to use json.simple to get things from this json file:
"Main": {
"Part1":{
"Length": 2,
"Flags": 2,
"Sequence": 4
},
"Part2":{
"Length": 2,
"Type":2,
"Main_Dest":4,
"Main_Source":4,
"Sequence":4,
"Data": {
"1":12,
"2":24
},
"Blank": 8
}
}
Basically, I want to reach the "Type" value in Part2, and on the way add all values. Meaning in the end I want to have the sum 10 (length+flags+sequence+length) and the number 2 for the value "Type". My main problem here is that I have to do it generically, so I can't just collect the values by name because they might change or additional values could be added. Only the value "Type" will always be called exactly that.
What I've done so far is this:
private static void parseJson() {
String path = "...config.json";
boolean count = false;
int sum = 0;
try {
FileReader reader = new FileReader(path);
JSONParser jsonParser = new JSONParser();
JSONObject jsonObject = (JSONObject) jsonParser.parse(reader);
jsonObject.entrySet();
JSONObject main = (JSONObject) jsonObject.get("Main");
for (Iterator iterator = main.keySet().iterator(); iterator.hasNext();){
String key = (String) iterator.next();
//this is where I'm stumped. Do I keep going into the JSONObject until I get to a value?
if (count){
sum += (int) sahara.get(key);
}
if (key.equals("Type")){
count = true;
}
}
System.out.println(skip);
} catch (Exception e) {
}
}
Obviously I don't really know what I'm doing with this. How do I iterate the lowest level in the json file?
As a little side question, which Json parser libraries should I use if I might sell my software? In other words, which doesn't cause licensing issues?
You can iterate over keys recursively, but you can't calculate sum, result will be unpredictable.
jsonObject.keySet not guarantee returns the keys in the same order as they appears in file.
Use the stream API for Json.
I have added the missing curly braces to fix your input.
{
"Main": {
"Part1":{
"Length": 2,
"Flags": 2,
"Sequence": 4
},
"Part2":{
"Length": 2,
"Type":2,
"Main_Dest":4,
"Main_Source":4,
"Sequence":4,
"Data": {
"1":12,
"2":24
},
"Blank": 8
}
}
}
This examples shows how to use the stream API.
// -*- compile-command: "javac -cp javax.json-1.0.jar q43737601.java && java -cp .:javax.json-1.0.jar q43737601"; -*-
import java.io.FileReader;
import javax.json.Json;
import javax.json.stream.JsonParser;
class q43737601
{
public static void main (String argv[]) throws Exception
{
String path = "config.json";
int sum = 0;
JsonParser p = Json.createParser (new FileReader (path));
while (p.hasNext()) {
JsonParser.Event e = p.next();
switch (e) {
case VALUE_NUMBER:
sum += Integer.parseInt(p.getString());
break;
case KEY_NAME:
if ("Type".equals(p.getString()))
System.out.println(sum);
break;
}
}
}
}
If you run it, it displays 10. The example sums up all numbers up to a key called "Type".
I tried the above example with OpenJDK. It was necessary to follow the steps explained in this answer. I had to set the class path (-cp) in the compile command.
I had tried a few example codes on suggester feature of ElasticSearch on the net but I couldn't solve my problem against the autocomplete solution
my index:
client.prepareIndex("kodcucom", "article", "1")
.setSource(putJsonDocument("ElasticSearch: Java",
"ElasticSeach provides Java API, thus it executes all operations " +
"asynchronously by using client object..",
new Date(),
new String[]{"elasticsearch"},
"Hüseyin Akdoğan")).execute().actionGet();
and I used suggestbuilder to obtain the keyword then scan through the content "field", and here is where the null pointer exception occurs due to no result
CompletionSuggestionBuilder skillNameSuggest = new CompletionSuggestionBuilder("skillNameSuggest");
skillNameSuggest.text("lien");
skillNameSuggest.field("content");
SuggestRequestBuilder suggestRequestBuilder = client.prepareSuggest("kodcucom").addSuggestion(skillNameSuggest);
SuggestResponse suggestResponse = suggestRequestBuilder.execute().actionGet();
Iterator<? extends Suggest.Suggestion.Entry.Option> iterator =
suggestResponse.getSuggest().getSuggestion("skillNameSuggest").iterator().next().getOptions().iterator();
Am I missing some filters or input criteria in order to get result? Any result should ok such as autocomplete or record found.
EDIT 1:
This is where I got the NPE and I could see that none of any result return at suggestResponse from debug mode
Iterator<? extends Suggest.Suggestion.Entry.Option> iterator =
suggestResponse.getSuggest().getSuggestion("skillNameSuggest").iterator().next().getOptions().iterator();
EDIT 2:
I am using 2.1.1 version of ElasticSearch Java API
EDIT 3:
I tried in splitting up the iterator line into several code blocks, the NPE occur at the last line when converting a set of data into iterator, but there is not much helping
Suggest tempSuggest = suggestResponse.getSuggest();
Suggestion tempSuggestion = tempSuggest.getSuggestion("skillNameSuggest");
Iterator tempIterator = tempSuggestion.iterator();
I see that the codes:
SuggestRequestBuilder suggestRequestBuilder = client.prepareSuggest("kodcucom").addSuggestion(skillNameSuggest);
SuggestResponse suggestResponse = suggestRequestBuilder.execute().actionGet();
has already consists a empty array/dataset, am I using the suggest request builder incorrectly?
In order to use completion feature, you need to dedicate one field, which will be called completion and you have to specify a special mapping for it.
For example:
"mappings": {
"article": {
"properties": {
"content": {
"type": "string"
},
"completion_suggest": {
"type": "completion"}
}
}
}
The completion_suggest field is the field we will use for the autocomplete function in the above code sample. After this mapping defination, the data must be indexing as follow:
curl -XPOST localhost:9200/kodcucom/article/1 -d '{
"content": "elasticsearch",
"completion_suggest": {
"input": [ "es", "elastic", "elasticsearch" ],
"output": "ElasticSearch"
}
}'
Then Java API can be used as follows for get suggestions:
CompletionSuggestionBuilder skillNameSuggest = new CompletionSuggestionBuilder("complete");
skillNameSuggest.text("es");
skillNameSuggest.field("completion_suggest");
SearchResponse searchResponse = client.prepareSearch("kodcucom")
.setTypes("article")
.setQuery(QueryBuilders.matchAllQuery())
.addSuggestion(skillNameSuggest)
.execute().actionGet();
CompletionSuggestion compSuggestion = searchResponse.getSuggest().getSuggestion("complete");
List<CompletionSuggestion.Entry> entryList = compSuggestion.getEntries();
if(entryList != null) {
CompletionSuggestion.Entry entry = entryList.get(0);
List<CompletionSuggestion.Entry.Option> options =entry.getOptions();
if(options != null) {
CompletionSuggestion.Entry.Option option = options.get(0);
System.out.println(option.getText().string());
}
}
Following link provides you the details of how to create a suggester index. https://www.elastic.co/blog/you-complete-me
Now, I use asynchronous Suggestionbuilder Java API to generate suggestions based on terms.
SearchRequestBuilder suggestionsExtractor = elasticsearchService.suggestionsExtractor("yourIndexName", "yourIndexType//not necessary", "name_suggest", term);
System.out.println(suggestionsExtractor);
Map<String,Object> suggestionMap = new HashMap<>();
suggestionsExtractor.execute(new ActionListener<SearchResponse>() {
#Override
public void onResponse(SearchResponse searchResponse) {
if(searchResponse.status().equals(RestStatus.OK)) {
searchResponse.getSuggest().getSuggestion("productsearch").getEntries().forEach(e -> {
e.getOptions().forEach(s -> {
ArrayList<Object> contents = new ArrayList<>();
suggestionMap.put(s.getText().string(), s.getScore());
});
});
}
}
#Override
public void onFailure(Exception e) {
Helper.sendErrorResponse(routingContext,new JsonObject().put("details","internal server error"));
e.printStackTrace();
}
});
Following is how suggestionbuilder is created.
public SearchRequestBuilder suggestionsExtractor(String indexName, String typeName, String field, String term) {
CompletionSuggestionBuilder csb = SuggestBuilders.completionSuggestion(field).text(term);
SearchRequestBuilder suggestBuilder = client.prepareSearch()
.suggest(new SuggestBuilder().addSuggestion(indexName, csb));
return suggestBuilder;
}
I'm using Eclipse Birt to generate report from a JSON File.
My JSON file look like this :
{
"cells":[
{
"type":"basic.Sensor",
"custom":{
"identifier":[
{
"name":"Name1",
"URI":"Value1"
},
{
"name":"Name4",
"URI":"Value4"
}
],
"classifier":[
{
"name":"Name2",
"URI":"Value2"
}
],
"output":[
{
"name":"Name3",
"URI":"Value3"
}
],
},
"image":{
"width":50,
"height":50,
"xlink:href":"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAIAAAACACAYAAADDPmHLAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAABEJAAARCQBQGfEVAAAABl0RVh0U29mdHdhcmUAd3Vi8f+k/EREURQtsda2Or/+nFLqP6T5Ecdi0aJFL85msz2Qxyf4JIumMAx/ClmWt23GmL1kO54CXANAVH+WiN4Sx7EoNVkU3Z41BDHMeXAxjvOxNr7RJjzHX7S/jAflwBxkJr/RwiOpWZ883Nzd+Wpld7tkBr/SJr7ZHZbHZeuVweSnPfniocMAWYwcGBafH0OoPamFGAaY4ZBZjmmFGAaY4ZBZjmmFGAaY4ZBZjmmFGAaY7/B94QnX08zxKLAAAAAElFTkSuQmCC"
}
}
},
{
"type":"basic.Sensor",
"custom":{
"identifier":[
{
"name":"Name1",
"URI":"Value1"
},
{
"name":"Name4",
"URI":"Value4"
}
],
"classifier":[
{
"name":"Name2",
"URI":"Value2"
}
],
"output":[
{
"name":"Name3",
"URI":"Value3"
}
],
},
"image":{
"width":50,
"height":50,
"xlink:href":"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAgAAAAIACAYAAAD0eNT6AAAACXBIWXMAAAsTAAALEwEAmpwYAAAKT2lDQ1BQaG90b3Nob3AgSUNDIHByb2ZpbGUAAHjanVNnVFPpFj333vRCS4iAlEtvUhUIIFJCi4AUkSYqIQkQSoghodkVUcERRUUEG8igiAOOjoCMFVEsDIoK2AfkIaKOg6OIisr74Xuja9igAQAAAgAIoAEAAAIACKABAAACAAigAQAAAgAIoAEAAAIACKABAAACAAigAQAAAgAIoAEAAAIADqhvprADeSsau00l5NAAAAAElFTkSuQmCC"
}
}
},
{
"type":"basic.Platform",
"custom":{
"identifier":[
{
"name":"Name1",
"URI":"Value1"
}
],
"classifier":[
{
"name":"Name2",
"URI":"Value2"
}
],
"output":[
{
"name":"Name3",
"URI":"Value3"
}
],
"image":{
"width":50,
"height":50,
"xlink:href":"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAQAAAA6TH0jqtg6U8EsCdnm3SpevSK7Pb85xABEMBuLAn2hxjRve7SFzYEaB/HhytLQ4ABRwCWBPvBKnRk6U8EkBeOD9f7iwAGHAGEYEmwDxLvzNKfCCDP8NGLQd3lY7D0JwI4kmlwfHhX6dTSXxsRAAHsWR7aUjc7uM5Wg=="
}
}
}
]
}
i have 3 cells and each one contains 1 Image 1 Name 1 Type and 3 Tables , this is what i have done so far :
what i'm struggling to do is a nested loop, i want to have for each object( Cell) in my JSON a paragraph numerated like this :
2.x Component cell's Name :
Image
Output Table
Identifier Table
Classifier Table
So to do this i need to itterate on each cell and then itterate on each table Output, identifier and classifier and i have no idea how can i do this, a nested loop. like a List which represent the number of cells, that contains 3 tables, one image , one name.
**Edit : **
this is the open method for the data set
// Grab the JSON file and place it in a string
fisTargetFile = new FileInputStream(new File("C:/Users/Sample Reports/moe.json"));
input = IOUtils.toString(fisTargetFile, "UTF-8");
// Store the contents in a variable
jsonData = input;
// Convert the String to a JSON object
myJSONObject = eval( '(' + jsonData + ' )' );
// Get the length of the object
len = myJSONObject.cells.length;
// Counter
count = 0;
Fetch method :
if(count < len) {
var name = myJSONObject.cells[count].attrs.text["text"];
var type = myJSONObject.cells[count].type;
var icon =myJSONObject.cells[count].attrs.image["xlink:href"];
icon = icon.split(",");
icon= icon[1];
imageDataBytes = icon;
row["name"] = name;
row["type"] = type;
row["icon"] = Base64ToBlob.toBytes(icon);
Logger.getAnonymousLogger().info( row["icon"]);
count++;
return true;
}
return false;
You want to use nested tables, there is a good tutorial showing how to link nested tables to an outer table: please watch carefully this demo first, in particular see how the sub-table is linked to the outer table through a dataset parameter.
Of course your case is more challenging because you need to do this with scripted datasets and multiple sub-tables. I already did something similar, you have to create one scripted dataset for each sub-table. Key-points are:
In "parameters" section of each sub-dataset, create one input parameter and name it for instance "systemID"
Create your sub-tables by "drag & drop" each dataset within the outer table
In "bindings" section of each sub-table, link parameter "systemID" to the ID field of the outer table
In "open" event of sub-datasets, access the value of the parameter with this expression: inputParams["systemID"] Thus you can filter related rows in "myJSONObject".
It is important to make sure "myJSONObject" is initialized once for all, otherwise performances could dramatically decrease if it is evaluated on each iteration. For example evaluate it in "initialize" event of the report.
That's it, it won't be easy but these elements should help to achieve this report.