How can I use a payload instead of form-data for log4javascript - log4javascript

I am bound to the restrictions of my webservice: It expects a json-payload!
So, doing something like
var ajaxAppender = new log4javascript.AjaxAppender("clientLogger");
var jsonLayout = new log4javascript.JsonLayout();
ajaxAppender.setLayout(jsonLayout);
log.addAppender(ajaxAppender);
won't work, as it creates two keys in the forms-collection (data and layout).
How can I, with built-in options, get a json-payload?

I've created a JsonAppender
function JsonAppender(url) {
var isSupported = true;
var successCallback = function(data, textStatus, jqXHR) { return; };
if (!url) {
isSupported = false;
}
this.setSuccessCallback = function(successCallbackParam) {
successCallback = successCallbackParam;
};
this.append = function (loggingEvent) {
if (!isSupported) {
return;
}
$.post(url, {
'logger': loggingEvent.logger.name,
'timestamp': loggingEvent.timeStampInMilliseconds,
'level': loggingEvent.level.name,
'url': window.location.href,
'message': loggingEvent.getCombinedMessages(),
'exception': loggingEvent.getThrowableStrRep()
}, successCallback, 'json');
};
}
JsonAppender.prototype = new log4javascript.Appender();
JsonAppender.prototype.toString = function() {
return 'JsonAppender';
};
log4javascript.JsonAppender = JsonAppender;
used like so
var logger = log4javascript.getLogger('clientLogger');
var jsonAppender = new JsonAppender(url);
logger.addAppender(jsonAppender);

According to log4javascript's change log, with version 1.4.5, there is no longer the need to write a custom appender, if the details sent by Log4Javascript suffice.
1.4.5 (20/2/2013)
- Changed AjaxAppender to send raw data rather than URL-encoded form data when
content-type is not "application/x-www-form-urlencoded"
https://github.com/DECK36/log4javascript/blob/master/changelog.txt
Simply adding the 'Content-Type' header to the AjaxAppender and setting it to 'application/json' is enough
ajaxAppender.addHeader("Content-Type", "application/json;charset=utf-8");
A quick test using fiddler shows that log4javascipt sends a collection of objects. Here's a sample of the payload:
[{
"logger": "myLogger",
"timestamp": 1441881152618,
"level": "DEBUG",
"url": "http://localhost:5117/Test.Html",
"message": "Testing message"
}]

Related

I'm creating an erp connector for a company with google data studio, but I don't know how this process works

const cc = DataStudioApp.createCommunityConnector();
function getAuthType() {
return cc.newAuthTypeResponse()
.setAuthType(cc.AuthType.USER_TOKEN)
.setHelpUrl('https://api.sigecloud.com.br/swagger/ui/index#/')
.build();
}
function resetAuth() {
var userTokenProperties = PropertiesService.getUserProperties();
userTokenProperties.deleteProperty('dscc.username');
userTokenProperties.deleteProperty('dscc.password');
}
function isAuthValid() {
var userProperties = PropertiesService.getUserProperties();
var userName = userProperties.getProperty('dscc.username');
var token = userProperties.getProperty('dscc.token');
var res = UrlFetchApp.fetch(`https://api.sigecloud.com.br/request/Pedidos/GetTodosPedidos&Authorization-Token${token}&User=${userName}&page=12&App=API APP`, { 'muteHttpExceptions': true });
return res.getResponseCode() == 200;
}
function getConfig() {
}
function getSchema() {
}
function getData() {
}
This is Manifest:
{
"timeZone": "America/Sao_Paulo",
"dependencies": {},
"exceptionLogging": "STACKDRIVER",
"runtimeVersion": "V8",
"dataStudio":{
"name": "Two Dogs Connector with Sige",
"description": "The unofficial conecctor to acess Sige Data",
"company": "Mateus C Rocha",
"logoUrl": "https://images.sympla.com.br/62ea7b9d69ec5.png",
"addOnUrl": "https://twodogs.com/br/quem-somos/",
"supportUrl": "https://twodogs.com/br/quem-somos/"
}
}
This error appears when I add the implementation ID generated when I select the test implementation option, in the google script
My api needs to receive: Page, user(constant value), token(constant value) and App(constant value)...
I don't know how it works, but I was hoping it wouldn't show errors, as I followed the documentation https://developers.google.com/looker-studio/connector/get-started

Error when merging multiple pdf files into one file in Google Drive

I used the following code (taken from PDF.CO) to merge multiple pdf files in Google Drive:
/**
* Initial Declaration and References
*/
// Get the active spreadsheet and the active sheet
ss = SpreadsheetApp.getActiveSpreadsheet();
ssid = ss.getId();
// Look in the same folder the sheet exists in. For example, if this template is in
// My Drive, it will return all of the files in My Drive.
var ssparents = DriveApp.getFileById(ssid).getParents();
// Loop through all the files and add the values to the spreadsheet.
var folder = ssparents.next();
/**
* Add PDF.co Menus in Google Spreadsheet
*/
function onOpen() {
var menuItems = [
{name: 'Get All PDF From Current Folder', functionName: 'getPDFFilesFromCurFolder'},
{name: 'Merge PDF URLs Listed In Cell', functionName: 'mergePDFDocuments'}
];
ss.addMenu('PDF.co', menuItems);
}
/**
* Get all PDF files from current folder
*/
function getPDFFilesFromCurFolder() {
var files = folder.getFiles();
var pdfUrlCell = ss.getRange("A4");
var allFileUrls = [];
while (files.hasNext()) {
var file = files.next();
var fileName = file.getName();
if(fileName.endsWith(".pdf")){
// Make File Pulblic accessible with URL so that it can be accessible with external API
var resource = {role: "reader", type: "anyone"};
Drive.Permissions.insert(resource, file.getId());
// Add Url
allFileUrls.push(file.getDownloadUrl());
}
pdfUrlCell.setValue(allFileUrls.join(","));
}
}
function getPDFcoApiKey(){
// Get PDF.co API Key Cell
let pdfCoAPIKeyCell = ss.getRange("B1");
return pdfCoAPIKeyCell.getValue();
}
/**
* Function which merges documents using PDF.co
*/
function mergePDFDocuments() {
// Get Cells for Input/Output
let pdfUrlCell = ss.getRange("A4");
let resultUrlCell = ss.getRange("B4");
let pdfUrl = pdfUrlCell.getValue();
// Prepare Payload
const data = {
"async": true, // As we have large volumn of PDF files, Enabling async mode
"name": "result",
"url": pdfUrl
};
// Prepare Request Options
const options = {
'method' : 'post',
'contentType': 'application/json',
'headers': {
"x-api-key": getPDFcoApiKey()
},
// Convert the JavaScript object to a JSON string.
'payload' : JSON.stringify(data)
};
// Get Response
// https://developers.google.com/apps-script/reference/url-fetch
const resp = UrlFetchApp.fetch('https://api.pdf.co/v1/pdf/merge', options);
// Response Json
const respJson = JSON.parse(resp.getContentText());
if(respJson.error){
console.error(respJson.message);
}
else{
// Job Success Callback
const successCallbackFn = function(){
// Upload file to Google Drive
uploadFile(respJson.url);
// Update Cell with result URL
resultUrlCell.setValue(respJson.url);
}
// Check PDF.co Job Status
checkPDFcoJobStatus(respJson.jobId, successCallbackFn);
}
}
/**
* Checks PDF.co Job Status
*/
function checkPDFcoJobStatus(jobId, successCallbackFn){
// Prepare Payload
const data = {
"jobid": jobId
};
// Prepare Request Options
const options = {
'method' : 'post',
'contentType': 'application/json',
'headers': {
"x-api-key": getPDFcoApiKey()
},
// Convert the JavaScript object to a JSON string.
'payload' : JSON.stringify(data)
};
// Get Response
// https://developers.google.com/apps-script/reference/url-fetch
const resp = UrlFetchApp.fetch('https://api.pdf.co/v1/job/check', options);
// Response Json
const respJson = JSON.parse(resp.getContentText());
if(respJson.status === "working"){
// Pause for 3 seconds
Utilities.sleep(3 * 1000);
// And check Job again
checkPDFcoJobStatus(jobId, successCallbackFn);
}
else if(respJson.status == "success"){
// Invoke Success Callback Function
successCallbackFn();
}
else {
console.error(`Job Failed with status ${respJson.status}`);
}
}
/**
* Save file URL to specific location
*/
function uploadFile(fileUrl) {
var fileContent = UrlFetchApp.fetch(fileUrl).getBlob();
folder.createFile(fileContent);
}
It runs perfectly the first time, but then gives an error:
Exception: Request failed for https://api.pdf.co returned code 402. Truncated server response: {"status":"error","errorCode":402,"error":true,"message":"Not enough credits, subscription expired or metered use is not allowed. Please review cre... (use muteHttpExceptions option to examine full response).

How can I make struct in go for object having array of object inside it?

I am using Vuejs on the frontend and Go language on the backend. My data variable has data in the following format.
var data = {
software_type: this.$props.selected,
selected_solutions: this.fromChildChecked,
};
By doing console.log(data)in frontend, I get following output.
On the backend side, I have struct on this format :
type Technology struct {
ID primitive.ObjectID `json:"_id,omitempty" bson:"_id,omitempty"`
SoftwareType string `json:"software_type" bson:"software_type"`
SelectedSolutions struct {
selectedSolutions []string
} `json:"selected_solutions" bson:"selected_solutions"`
}
I am quite sure about the problem that I am having and it might be due to the difference with the format of data that I am sending and the struct that I have made.
I am using MongoDB as a database.
By submitting the form, data comes to DB in the following format, which means, I am getting an empty object for selected_solutions.
{
"_id":{"$oid":"5f5a1fa8885112e153b5a890"},
"software_type":"Cross-channel Campain Mangment Software",
"selected_solutions":{}
}
This is the format that I expect to be on DB or something similar to below.
{
"_id":{"$oid":"5f5a1fa8885112e153b5a890"},
"software_type":"Cross-channel Campain Mangment Software",
"selected_solutions":{
Adobe Campaign: ["Business to Customer (B2C)", "Business to Business (B2B)"],
Marin Software: ["E-Government", "M-Commerce"],
}
}
How can I change struct to make it compatible with the data that I am trying to send? Thank you in advance for any help.
EDIT: This is how I am submitting data.
postUserDetails() {
var data = {
software_type: this.$props.selected,
selected_solutions: this.fromChildChecked,
};
console.log(data);
const requestOptions = {
method: "POST",
headers: { "Content-Type": "application/x-www-form-urlencoded" },
body: JSON.stringify(data),
};
fetch("http://localhost:8080/technology", requestOptions)
.then((response) => {
response.json().then((data) => {
if (data.result === "success") {
//this.response_message = "Registration Successfull";
console.log("data posted successfully");
} else if (data.result === "er") {
// this.response_message = "Reagestraion failed please try again";
console.log("failed to post data");
}
});
})
.catch((error) => {
console.error("error is", error);
});
},
mounted() {
this.postUserDetails();
},
This is the function for backend controller.
//TechnologyHandler handles checkbox selection for technology section
func TechnologyHandler(w http.ResponseWriter, r *http.Request) {
w.Header().Set("content-type", "application/json")
w.Header().Add("Access-Control-Allow-Credentials", "true")
var technologyChoices model.Technology
//var selectedSolution model.Selected
//reads request body and and stores it inside body
body, _ := ioutil.ReadAll(r.Body)
//body is a json object, to convert it into go variable json.Unmarshal()is used ,
//which converts json object to User object of go.
err := json.Unmarshal(body, &technologyChoices)
var res model.TechnologyResponseResult
if err != nil {
res.Error = err.Error()
json.NewEncoder(w).Encode(res)
return
}
collection, err := db.TechnologyDBCollection()
if err != nil {
res.Error = err.Error()
json.NewEncoder(w).Encode(res)
return
}
_, err = collection.InsertOne(context.TODO(), technologyChoices)
if err != nil {
res.Error = "Error While Creating Technology choices, Try Again"
res.Result = "er"
json.NewEncoder(w).Encode(res)
return
}
res.Result = "success"
json.NewEncoder(w).Encode(res)
return
}
Based on your database structure, selected_solutions is an object containing string arrays:
type Technology struct {
ID primitive.ObjectID `json:"_id,omitempty" bson:"_id,omitempty"`
SoftwareType string `json:"software_type" bson:"software_type"`
SelectedSolutions map[string][]string `json:"selected_solutions" bson:"selected_solutions"`
}

How to get Multiple Key Value in Dart Http

Please How Can I get this kind of API response in Flutter using http with FutureBuilder.
"GLODATA": {
"1000": {
"pname": "GLO 1.0GB/14days",
"price": "470",
"pld": "1000"
},
"1600.01": {
"pname": "GLO 2.0GB/30days",
"price": "940",
"pld": "1600.01"
},
"3750.01": {
"pname": "GLO 4.5GB/30days",
"price": "1900",
"pld": "3750.01"
},
"5000.01": {
"pname": "GLO 7.2GB/30days",
"price": "2430",
"pld": "5000.01"
}
},
I think in your case, you will need to do something like this:
Api:
Future<http.Response> getData() async {
final _api = "http://yourendpointhere";
http.Response response = await http.get(_api);
if (response.statusCode != 200) {
throw Exception("Request failed...");
}
return response;
}
Then consume your api:
http.Response response = await _apiInstance.getData();
if (response.body != null && response.body.isNotEmpty) {
String source = Utf8Decoder().convert(response.bodyBytes);
Map<String, Map<String, dynamic>> data = Map();
data = Map<String, Map<String, dynamic>>.from(json.decode(source));
}
After that, you can create a factory constructor in your model class, receiving that map and turning it into an instance of your class.

Dynatree init from custom json data

There is an example on the website on how to construct child nodes from custom data:
$("#tree").dynatree({
[…]
onLazyRead: function(node){
$.ajax({
url: […],
success: function(data, textStatus){
// In this sample we assume that the server returns JSON like
// { "status": "...", "result": [ {...}, {...}, ...]}
if(data.status == "ok"){
// Convert the response to a native Dynatree JavaScipt object.
var list = data.result;
res = [];
for(var i=0, l=list.length; i<l; i++){
var e = list[i];
res.push({title: "" + i + ": " + e.fcurr + "-" + e.tcurr + ":" + e.ukurs,
icon: false});
}
// PWS status OK
node.setLazyNodeStatus(DTNodeStatus_Ok);
node.addChild(res);
}else{
// Server returned an error condition: set node status accordingly
node.setLazyNodeStatus(DTNodeStatus_Error, {
tooltip: data.faultDetails,
info: data.faultString
});
}
}
});
[…]
});
But there is no mention on how to do this for the initialization of the tree. I tried the following:
initAjax: {
type: "POST",
url: "/doSomething",
data: ...
contentType: "application/json; charset=utf-8"
success: function(data, textStatus){
// In this sample we assume that the server returns JSON like
// { "status": "...", "result": [ {...}, {...}, ...]}
if(data.status == "ok"){
// Convert the response to a native Dynatree JavaScipt object.
var list = data.result;
res = [];
for(var i=0, l=list.length; i<l; i++){
var e = list[i];
res.push({title: "" + i + ": " + e.fcurr + "-" + e.tcurr + ":" + e.ukurs,
icon: false});
}
// PWS status OK
node.setLazyNodeStatus(DTNodeStatus_Ok);
node.addChild(res);
}else{
// Server returned an error condition: set node status accordingly
node.setLazyNodeStatus(DTNodeStatus_Error, {
tooltip: data.faultDetails,
info: data.faultString
});
}
}
},
But then I get an error saying success doesn't work and to use some other method, but there is no documentation on how to use the other method? Can anyone help me out here? I tried using dataFilter to filter out my json string that is being returned, but that didn't work; I tried to use onPostInit and postProcess but don't know exactly what to do since there is no documentation: Do I return the data string after its been reformated, do I return the json version of the data? do I just do data = format(data)?
Any help would be greatly appreciated.
I will be having a lot of status codes and need to do different things based on the code; such as if I have code 1 it means I need to change the class of the node to have red text; or if I return code 2 it means there was an internal error and I need to add that to the node text; etc.