Getting an array of users that edited a page - javascript

I am working on a user script for a Wikia community ( http://c.wikia.com ) and I need to get array of users (and possibly revision IDs) of a page. I have come up with the following code but cannot seem to make it work. Any help would be appreciated.
Code:
var revisions = [];
$.getJSON('/api.php', {
action: 'query',
prop: 'revisions',
titles: mw.config.get("wgPageName"),
rvprop: 'user',
rvlimit: '50',
format: 'json'
}, function (result) {
for (var i = 0; i < 50; i++) {
var revision = result.query.pages.page[i].revisions.user;
revisions.push(revision);
}
alert(revisions);
});

The query result looks something like this:
{
"query": {
"pages": {
"421588": {
"pageid": 421588,
"ns": 0,
"title": "Community Central",
"revisions": [
{
"user": "Mhadick"
},
{
"user": "Nblonkenfeld"
},
…
]
}
}
},
…
}
You'll notice that pages is an object with property named after the page id of the current page "421588" (judging from your code, you might be looking at the XML version of the response, you have to look at the JSON). To work with that, you can use something like:
var users = [];
$.getJSON('/api.php', {
action: 'query',
prop: 'revisions',
titles: mw.config.get("wgPageName"),
rvprop: 'user',
rvlimit: '50',
format: 'json'
}, function (result) {
var revisions = result.query.pages[mw.config.get("wgArticleId")].revisions;
$.each(revisions, function(key, revision) {
users.push(revision.user);
});
alert(users);
});

Related

Passing array of complex objects from view to controller using Ajax

In the controller I need to receive two parameters (detail and test), one is a List of a custom objects, the other is a string, I'm able two pass only one parameter (list of objects) when pass both I receive null values in the controller.
Resulting Json to controller:
[{
"detail": [{
"tag": "PIC330_620%2F_.PV_Out%23Value",
"color": "%2331c63e"
}, {
"tag": "A330_10%2F_.FbkFwdOut%23Value",
"color": "%238edeed"
}, {
"tag": "TIC330_603%2F_.PV_Out%23Value",
"color": "%23e8ea62"
}, {
"tag": "TI330_600%2F_.PV_Out%23Value",
"color": "%23f7cbb4"
}, {
"tag": "TIC311_602%2F_.MV%23Value",
"color": "%23ef935d"
}, {
"tag": "TIC311_602%2F_.PV_Out%23Value",
"color": "%23f28a9b"
}, {
"tag": "TIC310_600%2F_.MV%23Value",
"color": "%2385f968"
}, {
"tag": "TIC310_605%2F_.PV_Out%23Value",
"color": "%2308d687"
}],
"test": "lolo"
}]
//Generate list of objects
function getViewDetail() {
var details = [];
var tag;
var color;
var detail;
$('.tagContainer').each(function (i, obj) {
tag = $(this).find('.tag_label').text();
color = $(this).children('.colorpicker').val();
detail = { tag: encodeURIComponent(tag), color: encodeURIComponent(color) };
details.push(detail);
});
return details;
}
// Call Ajax
function sendParameters(){
var details = getViewDetail();
var list = [];
list.push({ detail: details, test: 'lolo' });
list = JSON.stringify(list);
console.log(list);
jQuery.ajax({
url: '#Url.Action("SaveView", "Batch")',
async: false,
data: list,
contentType: 'application/json',
dataType: 'json',
type: 'POST',
success: function (result) {
if (!result.success) {
showErrorMessage(result.title, result.message);
}
else {
showSuccessMessage(result.title, result.message);
}
}
});
}
//In the controller (abbreviated)
public JsonResult SaveView(IEnumerable<Detail> detail, string test)
{}
//class
public class Detail
{
string _tag;
string _color;
public string tag { get => _tag; set => _tag = value; }
public string color { get => _color; set => _color = value; }
}
Try this:
data = { detail: details, test: 'lolo' };
data = JSON.stringify(data);
And send it through ajax:
data: data,
Your action's signature is expecting two parameters, detail and test. What you were passing was a list of object with two properties detail and test on it. Got the difference ? In short your posting object should be like:
{
"detail": [...],
"test": "lolo"
}

Changing js array on a html

I want to manipulate an js array after a click but its not triggering.
example is here
https://datatables.net/examples/data_sources/js_array.html
what did i do is: (i need to re set dataset which is loaded into table previously please take a look at above example)
$(document).ready(function() {
$(".retrievemenu").click(function() {
//alert( this.id );
//$('#menus').hide();
var restid = this.id;
data = [
["sasa", "a", "a"]
];
$.post("server.php", {
retrievemenu: 1,
restid: restid
}, function(data) {
console.log(data);
$('#menus').hide();
$('#menus').DataTable({
data: data,
columns: [{
title: "Restaurant Name"
}, {
title: "Menu Name"
}, {
title: "Actions"
}
]
});
$('#menus').show();
});
});
});

Node.js loop through nested Javascript object

I want to have posts + attachments from Facebook so I can create a list of posts. The problem is that I want to put attributes: id, message and any attachment in a array for every post feed. I'm not sure whether I need to iterate objects inside a array or can I select the ID and get the related information.
Also I'm using async.waterfall() to get synchronous calls because I will make other calls that depend on the previous call.
I tried this to get the id, message and src url of attachment:
var async = require("async");
var graph = require('fbgraph');
async.waterfall([
getFeed,
getPostPicture,
], function (err, result) {
});
function getFeed(callback) {
graph.get("/.../feed" + "?fields=message,attachments&access_token=APPID|APPSECRET", function(err, res) {
callback(null, res);
});
}
function getPostPicture(arg1, callback) {
var feedData = arg1.data;
for(var i in feedData)
{
var id = feedData[i].id;
var message = feedData[i].message;
var feedAttachment = feedData[i].attachments
for (var j in feedAttachment)
{
var attachment = feedAttachment.data;
var attachmentURL = attachment[i].src;
for (var j in attachmentURL)
{
var attachmentURL = feedAttachment.src;
}
}
}
console.log(attachment);
}
Above will output:
[ { description: 'post message 1',
media: { image: [Object] },
target:
{ id: '...',
url: 'https://www.facebook.com/.../photos/a............/.../?type=3' },
title: 'Timeline Photos',
type: 'photo',
url: 'https://www.facebook.com/.../photos/a............/.../?type=3' } ]
Below is the response where I first called graph.get in the source code
and I need { data -> [message, id, attachments -> data[src] ]}
{
"data": [
{
"message": "post message 1",
"id": "..._...",
"attachments": {
"data": [
{
"description": "picture 1",
"media": {
"image": {
"height": 256,
"src": "https://scontent.xx.fbcdn.net/v/t1.0-9/..._..._..._n.png?oh=...&oe=...",
"width": 256
}
},
"target": {
"id": "...",
"url": "https://www.facebook.com/.../photos/a............/.../?type=3"
},
"title": "Timeline Photos",
"type": "photo",
"url": "https://www.facebook.com/.../photos/a............./..../?type=3"
}
]
}
},
{
"message": "Test status update 123",
"id": "..._..."
}
],
"paging": {
"previous": "https://graph.facebook.com/v2.8/.../feed?fields=message,attachments&format=json&since=...&access_token=...&limit=25&__paging_token=enc_...&__previous=1",
"next": "https://graph.facebook.com/v2.8/.../feed?fields=message,attachments&format=json&access_token=...&limit=25&until=...&__paging_token=enc_..."
}
}
When you are using the for loop in getPostPicture function, the i variable is actually the element in the array feedData, so you have to i.id or i.attachments and i.message. Also I think since you are using same j in 2 loops with one nested inside the other, it also won't work properly, so you might have to change that also, and explain you question with the kind of output you are expecting.

Tableau json API WebConnector

I've written the following tableau webconnector to pull data from an internal API, using earthquakeUSGS.html as a guideline (https://github.com/tableau/webdataconnector). The API returns json (see code below). I've been using the "Web data connector simulator 2.0" and all has been going well. I get the correct Table, however, Im unable to "Fetch Table Data". As this is my first js script, Im very sure that is were the error is. To iterate through the data I used the answer from Korijn in this post Iterate through nested json object array
The Problem: Is probably with the js iterator over the json object. If anyone can take a look at the json (below), and have a look at my iterator, I would greatly appreciate it. This is what makes it impossible for me to fetch data.
test.js
(function() {
// Create the connector object
var myConnector = tableau.makeConnector();
// Define the schema
myConnector.getSchema = function(schemaCallback) {
var cols = [{
id: "prog",
alias: "PrognosisTime",
dataType: tableau.dataTypeEnum.string
}, {
id: "start",
alias: "Start",
dataType: tableau.dataTypeEnum.date
}, {
id: "val",
alias: "Value",
dataType: tableau.dataTypeEnum.float
}];
var tableSchema = {
id: "table",
alias: "187",
columns: cols
};
schemaCallback([tableSchema]);
};
// Download the data
myConnector.getData = function(table, doneCallback) {
$.getJSON("http://myapi.com/119%2C7777/Flattened?start=today&end=today&timeZone=CET&asOf=now&aggregation=None", function(resp) {
var feat = resp.features,
tableData = [];
tableData.push(
{"table":feat.properties.table}
);
// Iterate over the JSON object
//var SeriesId = feat.SeriesId
for(var i = 0; i <feat.DataPoints.length; i++){
var PrognosisTime = feat.DataPoints.PrognosisTime;
var Start = feat.DataPoints.Start;
var Value = feat.DataPoints.Value;
}
table.appendRows(tableData);
doneCallback();
});
};
tableau.registerConnector(myConnector);
// Create event listeners for when the user submits the form
$(document).ready(function() {
$("#submitButton").click(function() {
tableau.connectionName = "Neas"; // This will be the data source name in Tableau
tableau.submit(); // This sends the connector object to Tableau
});
});
})();
json from API
[
{
"SeriesId": 119,
"DataPoints": [
{
"PrognosisTime": null,
"Start": "2016-08-24T00:00:00",
"Value": 26.19
},
{
"PrognosisTime": null,
"Start": "2016-08-24T01:00:00",
"Value": 23.9
},
{
"PrognosisTime": null,
"Start": "2016-08-24T02:00:00",
"Value": 22.82
}
]
},
{
"SeriesId": 7777,
"DataPoints": [
{
"PrognosisTime": null,
"Start": "2016-08-24T00:00:00",
"Value": 36.39
},
{
"PrognosisTime": null,
"Start": "2016-08-24T00:15:00",
"Value": 28.81
},
{
"PrognosisTime": null,
"Start": "2016-08-24T00:30:00",
"Value": 24.28
}
]
}
]
The problem is this line:
var feat = resp.features
resp is an array from your JSON, there is nothing called features. So, simply iterate over resp (or feat = resp) and pull out your DataPoints array.

count json lines dynamically

I asked this question earlier this morning
"here is my JSON file :
[
{
"Week": "1145",
"Sev_Logged": "3_major",
"From": "IN1"
},
{
"Week": "1145",
"Sev_Logged": "4_minor",
"From": "IN1"
},
{
"Week": "1145",
"Sev_Logged": "4_minor",
"From": "IN1"
},
{
"Week": "1145",
"Sev_Logged": "4_minor",
"From": "IN1"
},
{
"Week": "1145",
"Sev_Logged": "4_minor",
"From": "IN1"
},
{
"Week": "1145",
"Sev_Logged": "4_minor",
"From": "IN2"
},
{
"Week": "1145",
"Sev_Logged": "3_major",
"From": "IN2"
},
];
I want to count the "from : IN1" field for each "week", per example for week : 1145 i'd get : 3, and for "From : IN2" i'd get 2
Thanks"
Thank you VDP for your answer, so I did this :
My store is now like :
Ext.define('Metrics.store.GraphData', {
extend : 'Ext.data.Store',
model : 'Metrics.model.GraphData',
autoload : true,
proxy : {
type : 'ajax',
url : 'data/metrics_data.json',
reader : {
type : 'json',
root : 'data',
successProperty : 'success'
}
},
//data : GraphData, //povide inline data or load using proxy
countBy: function(param){
var count = {};
this.each(function(item){
var type = item.get(param);
if (Ext.isDefined(count[type])){
count[type]++;
} else {
count[type] = 1;
}
});
return count;
}
});
And my model :
Ext.define('Metrics.model.GraphData', {
extend: 'Ext.data.Model',
//fields: ['week', 'sev']
fields : [
{name: 'Week', type: 'int'},
{name: 'Sev_Logged', type: 'string'},
{name: 'From', type: 'string'}
]
});
Since i'm using extjs 4 with MVC model, I have made a controller wich controls the event of a button, right now it looks like this :
launchGraph : function(button){
console.log('clicked the apply button');
var chartStore = this.getGraphDataStore();
chartStore.load({
callback: this.onGraphDataLoad,
scope: this,
console.log(chartStore.countBy("From"))
});
But when I click the apply button I get this error in my controller :
"Uncaught SyntaxError: Unexpected token . "
And it points to the line :
"console.log(chartStore.countBy("From"))"
It seems like i have an error in the referencing to my store. Any ideas?
If var jsonData is the array resulting from parsing the json shown above, this will give you an object with the counts of each depending on the parameter you use..
function CountBy(parameter) {
var count = {};
for (var i = 0; i < jsonData.length; i++) {
var type = jsonData[i][parameter];
if (count[type] === undefined) {
count[type] = 1;
} else {
count[type]++;
}
}
return count;
}
Result:
CountBy("From") => {"IN1" : 5, "IN2" : 2}
CountBy("Week") => {"1145" : 7}
CountBy("Sev_Logged") => {"3_major": 2, "4_minor": 5}
If you are using the array you provide you can just use the mimikomi's answer or a similar ExtJS version of it:
here is a fiddle
function countBy(data, param) {
var count = {};
Ext.each(data, function(item){
var type = item[param];
if (Ext.isDefined(count[type])) {
count[type]++;
} else {
count[type] = 1;
}
});
return count;
}
If you load that json from an external location it's best practice to load it in a store. You define a model, a store and add 'special' functions to your store for example.
Ext.define('Week', {
extend: 'Ext.data.Model',
fields: [
{name: 'Week', type: 'int'},
{name: 'Sev_Logged', type: 'string'},
{name: 'From', type: 'string'}
]
});
var store = Ext.create('Ext.data.Store', {
model: 'Week',
data : data, //povide inline data or load using proxy
countBy: function(param){
var count = {};
this.each(function(item){
var type = item.get(param);
if (Ext.isDefined(count[type])){
count[type]++;
} else {
count[type] = 1;
}
});
return count;
}
});
var countObject = store.countBy("From");
alert(Ext.encode(countObject));
//chrome developper tools, safari, opera can show us the contents of objects in a log too. IE, FF however only tell us it is an object. (pretty useless)
console.log(countObject);
//you can chose you're favorite notation to retreve the value (but I hope you knew this, it's pretty basic javascript)
console.log(countObject.IN1);
console.log(countObject['IN2']);
Here is a fiddle.
More info on loading json dynamically into a store via ajax (using a proxy)

Categories

Resources