I want to create 2d arrays with the Rollbase API and store them in client-side variables. How do I do this?
This is what I tried but it just returns undefined:
var clientArray; function myCallback(values) { clientArray = values; } rbf_selectQuery("SELECT field1#value,COUNT(field1#value) FROM object1 GROUP BY field1#value", 1000, myCallback);
alert(clientArray);
Thank you,
Greg
Apologies for coming back so late. This is what happens when you mark a lot of stuff as TODO. Hope this still helps you.
<div id="div1"> <script> function renderChart(labels, values) { // variables for chart var canvasWidth = 600; var canvasHeight = 400; var pieXCoordinate = 150; var pieYCoordinate = 200; var pieRadius = 100; // create canvas var rIndustry = Raphael(document.getElementById("div1"), canvasWidth, canvasHeight); // create pie chart var pieIndustry = rIndustry.piechart(pieXCoordinate, pieYCoordinate, pieRadius, values, { legend: labels, legendpos: "east" }); } $(document).on('chartDataAvailable', function(e, labels, values) { renderChart(labels, values); }); rbf_selectQuery("select R281410#value, sum(Stock_Value) from stock1 group by R281410#value", 1000, function(values) { // parse your data into 2 1D arrays var industryLabels = ["Manufacturing","Financial Services","IT"]; // and one for values: var industryValues = [43,20,18]; $(document).trigger('chartDataAvailable', [ industryLabels, industryValues ]); }); </script>
Please place all data processing code into your callback function, not just after API call. AJAX is asynchronous process.
I'm sorry I don't understand -- can you demonstrate by rewriting my code above?
Thank you,
Greg
Hi,
This is how to get the 2d array values, need to add a loop which in my sample is a for loop, see code below
function myCallback(values) {
for(x=0; x<values.length; x++) {
//[x][0] represent your 1st parameter in the query
//[x][1] represent your 2nd parameter in the query and so on..
alert(values[x][0] +"---"+ +values[x][1]);
}
}
rbf_selectQuery("SELECT field1#value,COUNT(field1#value) FROM object1 GROUP BY field1#value", 1000, myCallback);
Hope this may help.
Regards,
Orchid
UPDATE: Storing 2d array to variable
var clientArray = []; function myCallback(values) { for(x=0; x<values.length; x++) { //[x][0] represent your 1st parameter in the query //[x][1] represent your 2nd parameter in the query and so on.. clientArray[x] = values[x][0] +"---"+ +values[x][1]; } alert(clientArray); } rbf_selectQuery("SELECT field1#value,COUNT(field1#value) FROM object1 GROUP BY field1#value", 1000, myCallback);
Regards,
Orchid
Thank you, Orchid. So I think to get the array into the variable is as straightforward as
var clientArray = [];
function myCallback(values) {
clientArray = values;
}
alert(clientArray);
}
rbf_selectQuery("SELECT field1#value,COUNT(field1#value) FROM object1 GROUP BY field1#value", 1000, myCallback);
But if the alert statement comes outside of the callback function (or if I try to use the clientArray variable in any way outside of the function) it doesn't work. I want to store the array in the client-side variable so I can use it in the UI, so I need to access the variable outside of the callback function.
Is there a way to do this with rbf_selectQuery? Or should it be done with an EVAL block and rbv_api.selectQuery? If so, what would that code look like?
Thank you,
Greg
Even if you declare clientArray as global (outside any function), the call to rbf_selectQuery is async. Your myCallback function which sets the clientArray is not guaranteed to run first before the alert statement.
So how do I store an array from the Rollbase database in a client-side variable?
p.s. if I put the AJAX calls and callback functions to store them in variables in a js file linked in the portal header or footer, will those calls run before the page content is loaded so that I can use the client-side array variables in pages? Or is there another way to force all of the calls to run before page content is loaded?
It is not about assigning variable, it is about when you will use it. Immediately after AJAX call result is undefined, as you have observed.
So how do I store an array from the Rollbase database in a client-side variable?
Your code is correct, sorry mine is a long method. And yes selectQuery is async, you may consider having timeout to your alert.
var clientArray; function myCallback(values) { clientArray = values; } rbf_selectQuery("SELECT field1#value,COUNT(field1#value) FROM object1 GROUP BY field1#value", 1000, myCallback); setTimeout("alert(clientArray);", 1000);
Regards,
Orchid
setTimeout is never a good idea. Network lag to server slowdown, anything can affect the time taken by the selectQuery to respond back with data. The code assumes that clientArray will contain values after 1sec.
A possible solution would be to write code based on custom events. Look here for a Javascript only way and here for a jQuery specific solution. I'd prefer the jQuery solution as Rollbase incorporates jQuery libraries.
function whatIWantToDoWithValuesInUI(queryResults) { ... } function selectQueryCallback(values) { // Trigger a custom event $.event.trigger('selectQueryEvent', { result: values }); } // Register to listen to the custom event $(document).bind('selectQueryEvent', function(e) { // e.result will have values here // e.anything will have anything passed in the event object above whatIWantToDoWithValuesInUI(e.result); }); rbf_selectQuery("SELECT field1#value,COUNT(field1#value) FROM object1 GROUP BY field1#value", 1000, selectQueryCallback);
Thank you, Santosh.
Since it seems that what I am trying to do is a bit uncommon, I want to make sure I am taking the right approach: my goal is to build custom charts in the portal for a CRM-like application using a client-side javascript charting library. For example, a pie chart will show the breakdown of opportunities by industry. What I thought made sense was to run the selectQuery to get the 2d matrix of something like
Manufacturing 43
Financial Services 20
IT 18
... and so on, then pass that array to a client-side variable which can be used to generate the chart. That's where this question comes up as to how to use the results of the async AJAX call outside of the callback function. I want to set all of these variables in one place, like a JS file in the portal footer, to be able to manage them more effectively. I think the other option of wrapping all the individual charts in the script components on multiple portal pages in separate callback functions will get too cumbersome.
So does this approach make sense or is there a better way to do this?
Thank you,
Greg
I would recommend you to consider server-side APIs to prepare HTML on server side. This should work unless you wish to process user's input dynamically.
Server-side APIs are synchronous (unlike AJAX), so you could use results in familiar way.
Thank you.
When I use the server-side API with this code:
<script> var clientArray= "#EVAL[rbv_api.selectQuery('SELECT field1#value,COUNT(field1#value) FROM object1 GROUP BY field1#value', 1000)]"; alert(clientArray); </script>
I get this alert: "org.mozilla.javascript.NativeJavaArray@67a4e0d1".
Can I pass a 2d array from the server-side API to a client-side variable?
"..and so on, then pass that array to a client-side variable which can be used to generate the chart. That's where this question comes up as to how to use the results of the async AJAX call outside of the callback function"
The custom events can help you with precisely that. Along with the event you can pass arbitrary data that listeners can get when the event is fired.
What charting library are you using? And share a sample chart generation code assuming the results are available. I'll see if I can get a working example for you using selectQuery.
But you're on the right track. Just add code (inside EVAL block) to extract values you need.
Hi!!
I think you can use server-side API it trued because Client -side API is AJAX concept . it work to 1 round trip ,1 request and 1 response . so you can use server-side api by Eval blog for get value to variable and if use want to display array for monitor. you can use "JSON.stringify(data)" .
I hope to help you.
Regards
BOY
Thank you very much, Santosh. I am using g.Raphael (http://g.raphaeljs.com/). Code for a simple chart following the example of a breakdown of opportunities by industry is as follows:
<div id="div1"> <script> // ...at this point in the code the client-side 2d array is already parsed into two 1d arrays, one for labels: var industryLabels = ["Manufacturing","Financial Services","IT"]; // and one for values: var industryValues = [43,20,18]; // variables for chart var canvasWidth = 600; var canvasHeight = 400; var pieXCoordinate = 150; var pieYCoordinate = 200; var pieRadius = 100; // create canvas var rIndustry = Raphael(document.getElementById("div1"), canvasWidth, canvasHeight); // create pie chart var pieIndustry = rIndustry.piechart(pieXCoordinate, pieYCoordinate, pieRadius, industryValues, { legend: industryLabels, legendpos: "east" }); </script>
If you can show me the code for the custom event to create the client-side Javascript 2d array that would be awesome -- thank you!
Thank you, BOY. When I try JSON.stringify it just turns the value of org.mozilla.javascript.NativeJavaArray@67a4e0d1 into a string "org.mozilla.javascript.NativeJavaArray@67a4e0d1", it does not create an array. Am I missing something?
Apologies for coming back so late. This is what happens when you mark a lot of stuff as TODO. Hope this still helps you.
<div id="div1"> <script> function renderChart(labels, values) { // variables for chart var canvasWidth = 600; var canvasHeight = 400; var pieXCoordinate = 150; var pieYCoordinate = 200; var pieRadius = 100; // create canvas var rIndustry = Raphael(document.getElementById("div1"), canvasWidth, canvasHeight); // create pie chart var pieIndustry = rIndustry.piechart(pieXCoordinate, pieYCoordinate, pieRadius, values, { legend: labels, legendpos: "east" }); } $(document).on('chartDataAvailable', function(e, labels, values) { renderChart(labels, values); }); rbf_selectQuery("select R281410#value, sum(Stock_Value) from stock1 group by R281410#value", 1000, function(values) { // parse your data into 2 1D arrays var industryLabels = ["Manufacturing","Financial Services","IT"]; // and one for values: var industryValues = [43,20,18]; $(document).trigger('chartDataAvailable', [ industryLabels, industryValues ]); }); </script>
Awesome, thank you so much, Santosh!!
Greg