JSON data not loading - ExtJS - json

I cannot get any of my json data to load into my combobox. Here's my code:
app/data/mydata.json
{
images: [
{name: 'Image one', url:'/GetImage.php?id=1', size:46.5, lastmod: new Date(2007, 10, 29)},
{name: 'Image Two', url:'/GetImage.php?id=2', size:43.2, lastmod: new Date(2007, 10, 30)}
]
}
inside my app.js
var store4 = new Ext.data.JsonStore({
// store configs
storeId: 'myStore',
autoLoad: true,
proxy: {
type: 'ajax',
url: 'app/data/mydata.json',
reader: {
type: 'json',
root: 'images',
idProperty: 'name'
}
},
});...
my combobox inside app.js
{ xtype: 'combobox', queryMode: 'local', padding: 5, store: store4, displayField: 'name', typeAhead: true, emptyText: 'JSON', id: 'test' },
Any ideas?
Cheers!

That isn't valid JSON:
Labels should be wrapped in quotes, eg "name". You should also use double quotes, not single for quoting strings.
You can't use new Date() in JSON, it's not valid. Have a look at Ext.data.Field and the information around the dateFormat parameter. You send the date back as a string and give it a format so Ext can parse it for you.
Also, you're missing field definitions. You need to create an Ext.data.Model subclass with the fields you're going to use in the store.
Ext.define('Image', {
extend: 'Ext.data.Model',
fields: ['name', 'url', 'size']
});
var store = new Ext.data.Store({
model: 'Image',
// ..
});

Related

How to implement Dynamic Grid in Extjs?

I want to implement dynamic grid in Extjs. I have found this How do you create table columns and fields from json? (Dynamic Grid) and the accepted answer looks good.
In my case I have no proxy store but a proxy model:
fields: [ {name: 'id', type: 'int', persist: false},
{name: 'gender', type: 'auto'},
{name: 'name', type: 'auto'},
{name: 'age', type: 'int'}],
identifier: 'sequential', // to generate -1, -2 etc on the client
proxy: {
type: 'rest',
idParam: "id",
url:'http://localhost:3000/posts',
api:
{
read : 'http://localhost:3000/db',
create: 'http://localhost:3000/posts',
update : 'http://localhost:3000/posts' ,
destroy : 'http://localhost:3000/posts'
},
headers: {'Content-Type': "application/json" },
reader: {
type: 'json',
rootProperty:'posts',
totalProperty: 'total'
},
writer: {
type: 'json'
}
My store looks like is:
model: 'ThemeApp.model.peopleModel',
storeId: 'peopleStore',
pageSize: 500,
autoLoad: true,
autoSync: true,
pageSize: 5,
autoLoad: {start: 0, limit: 5},
autoSync: true,
sorters: [{
property : 'age',
direction:'ASC'
}],
groupField: 'gender'
});
In my view I have defined columns:[] But I don't know where to call metachange function.
Can anyone tell me where to use metachange function and should I use metachange function of store or proxy?
Generally you don't want to configure proxy on the model, that is only useful when you want to use standalone Model instances without a store.
Move the proxy config to the Store, and make the server respond to read requests with additional metadata object, which you can then use in the metachange event handler to configure the grid.
Using Reader metadata is the right way to do "dynamic" Grids.

Extjs 5 XTemplate with JSON store data

I need help with my xtemplate and store with proxy. No matter what I am trying, I am stuck in this problem. The xtemplate is only showing data from a store without using a proxy.
Working store:
Ext.create('Ext.data.Store', {
storeId : 'viewStore',
model : 'dataview_model',
data : [
{statistic: '213213', description: 'Hallo'},
{statistic: '534345', description: 'Alloh'},
]
});
Working Xtemplate and data config
xtype: 'component',
cls: 'kpi-tiles',
id: 'statisticsBoxes',
height: 100,
tpl: [
'<div class="kpi-meta">',
'<tpl for=".">',
'<span>',
'<div class="statsDiv">{statistic}</div> {description}',
'</span>',
'</tpl>',
'</div>'
],
data: [{
description: Ext.getStore('statisticsStore').getAt(0).data.statistic,
statistic: Ext.getStore('viewStore').getAt(0).data.statistic
},{
description: Ext.getStore('viewStore').getAt(1).data.description,
statistic: Ext.getStore('viewStore').getAt(1).data.statistic
}],
But when I am changing the data for the template so it will load data from the Statistics store, the following error occurs in the console.log: Uncaught TypeError: Cannot read property 'getAt' of undefined.
Data config:
data: [{
description: 'the description',
statistic: Ext.getStore('statisticsStore').getAt(0).data.statistic
}],
Statistics store:
Ext.define('ExecDashboard.store.Statistics', {
extend: 'Ext.data.Store',
alias: 'store.statistics',
storeId: 'statisticsStore',
model: 'ExecDashboard.model.Statistics',
proxy: {
type: 'ajax',
url: '/statistics',
reader: 'json'
}
});
Produces the following JSON:
[{"statistic":"1"}, {"statistic":"2"}]
The store is loaded in the viewModel:
stores: {
Statistics: {
type: 'statistics',
autoLoad: true
}
}
I think the problem is that the store is not loaded at that moment. But I don't know how to solve this problem. I know that 'Ext.getStore('statisticsStore').getAt(0).data.statistic' works in the console.log when the store is loaded.
Use an Ext.view.View, that's exactly what the class is for:
xtype: 'dataview',
cls: 'kpi-tiles kpi-meta',
id: 'statisticsBoxes',
height: 100,
itemSelector: '.statsDiv',
tpl: [
'<tpl for=".">',
'<span>',
'<div class="statsDiv">{statistic}</div> {description}',
'</span>'
'</tpl>'
],
store: 'statisticsStore'
You probably need to set autoLoad: true on your store.
An event listener on the store in my viewModel solves the problem.
Statistics: {
type: 'statistics',
autoLoad: true,
listeners: {
load: function(){
var data = [{"description": "New", "statistic" : this.data.items[0].data.statistic}];
Ext.getCmp('statisticsBoxes').update(data);
}
}
}
When the store is loaded, the event will be fired which updates the Xtemplate with new data

JSON response with various data types

I have a JSON response like this
"{"total":1,"userBeanId":300,"list":[{"errors":[],"success":true,"liferayUserId":31503,"companyId":null,"groupId":null,"locale":null,"status":null,"liferayUserGroupId":null,"idProvider":null,"idClient":null,"userType":4,"userId":200,"email":"xpto#gmail.com","telefone":"999999999","nome":"MYNAME","role":"MY_ROLE","perfil":"Administrator","lastName":null}],"success":true}"
and what I have is a store that reads the list content, like this
"Ext.define('
MYPROJECT.store.Profiles', {
extend: 'Ext.data.Store',
model: 'MYPROJECT.model.Profile',
autoLoad: true,
pageSize: 10,
remoteSort: true,
remoteFilter: true,
proxy: {
type: 'ajax',
api: {
read: '/delegate/rlapi-common/profile/list'
},
enablePaging: true,
reader: {
type: 'json',
root: 'list',
successProperty: 'success'
}
}
});"
and the store "reads" the list successfully. However, I'd like to be able to access the "userBeanId" field as well. Is there any way I can access it by this store (by changing the root to something on an upper-level)? It confuses me as the store "maps" to a model and the userBeanId doesn't fit in the model.
Model:
Ext.define('MYPROJECT.model.Profile', {
extend: 'Ext.data.Model',
fields: [
'userId',
'nome',
'telefone',
'email',
'role',
'perfil'
],
});
You can access store.proxy.reader.rawData to get the most recently loaded JSON. As you suggested, it doesn't make sense being part of the model, but you can read extra meta info via the reader.

extJs - populate grid panel with array of strings

I receive an array of strings from the server.
How can I populate my grid panel if the data is not in key-value format?
Here is the response:
{"result":true,"data":["dep1","dep2","dep3"],"totalCount":3}
Here is my grid panel
xtype: 'gridpanel',
flex: 1,
itemId: 'departmentsGridPanel',
title: '',
store: new Ext.data.ArrayStore({
autoLoad: true,
fields: [
'department'
],
proxy: {
type: 'ajax',
url: 'FilteringDataServlet?filterColumn=avdeling',
reader: {
type: 'json',
root: 'data'
}
}
}),
columns: [{
text: 'Avdeling',
flex: 1,
dataIndex: 'department'
}],
Then you should use Ext.data.reader.Array with mapping parameter.
Employee = Ext.define('Employee', {
extend: 'Ext.data.Model',
fields: [
{name: 'name', mapping: 0}, // "mapping" only needed if an "id" field is present which
{name: 'occupation', mapping: 1} // precludes using the ordinal position as the index.
]
});
I have solved this by adding load listener to my store and modifying the data there
listeners: {
load: function(store, records, success, opts) {
store.each(function(record) {
record.set('department', record.raw);
});
}
}

EXTJS 4 Json nested data in grid panel

This topic has been discussed several times on the web but all subjects none helped me solve my problem.
My javascript code receives the JSON nested data. All JSON data Level 1 data are transcribed in the grid panel but all child data none.
I have tried so many ways but impossible.
That's why I'm asking you to help me please.
My JSON:
{
"success":true,
"error":false,
"redirectUrl":null,
"fund":[{
"cat_id":1,
"catname":"Europe OE Japan Large-Cap Equity",
"region":{
"region_id":2,
"region_name":"JAPAN"
}
},{
"cat_id":2,
"catname":"Europe OE Europe Large-Cap Growth Equity",
"region":{
"region_id":1,
"region_name":"EUROPE"
}
}]
}
MY model:
var Recommended = new function() {
this.DataModel = function() {
Ext.define('Fund', {
extend: 'Ext.data.Model',
fields: [{
name: 'catname',
type: 'string'
},{
name: 'cat_id',
type: 'int'
}],
proxy :{
type: 'rest',
url: application +'directory/function',
reader: {
type: 'json',
root: 'fund'
}
},
associations: [{
type: 'hasOne',
model: 'Region',
primaryKey: 'region_id',
name:'region'
}]
});
Ext.define('Region', {
extend: 'Ext.data.Model',
fields: [{
name: 'region_name',
type: 'string'
},{
name: 'region_id',
type: 'int'
}]
});
}
My Store & grid Panel:
this.JSONstore = function() {
var storeRecommended;
storeRecommended = Ext.create('Ext.data.Store', {
model: 'Fund',
autoLoad:true,
groupField: 'region_name'
});
var colModel =
[
{
text: 'REGION',
width: 200,
dataIndex: 'region_name',
name:'region_name',
mapping:'region.region_name'
},{
text: 'MORNINGSTAR',
width: 300,
dataIndex: 'catname',
name:'catname'
}
];
var groupingFeature = Ext.create('Ext.grid.feature.Grouping',{
groupHeaderTpl: 'Classe: {name} ({rows.length} Item{[values.rows.length > 1 ? "s" : ""]})',
hideGroupedHeader: false
});
var grid = Ext.create('Ext.grid.Panel', {
renderTo: 'recommendedlists',
collapsible: true,
iconCls: 'icon-grid',
frame: true,
store: storeRecommended,
width: 1200,
height: 400,
title: 'Test',
resizable: true,
features: [groupingFeature],
columns: colModel,
fbar : ['->', {
text:'Clear Grouping',
iconCls: 'icon-clear-group',
handler : function(){
groupingFeature.disable();
}
}]
});
}
this.initControlsOnload = function() {
Recommended.DataModel();
Recommended.JSONstore();
}
} // close Recommended function
The problem is your store bound to the grid knows nothing about Regions. It stores Funds. So you can't ask for a column to map to a data property that's not in the store.
The store is flat list of Fund records. And sure an individual Fund itself might know about the Region it belongs to, but the store containing a list of funds does not.
What to do?
What needs to happen is flattening out of your data structure on the client side. Why? Because the grid is flat. If you had multiple regions per fund - then we would be talking about a different solution.
How to do that?
If you control the server side of this app then add a Region field to the Fund object, then your data set is simple, straight forward and more importantly flat. If you can't (or don't want to) change the server side, then you can change the client side Model mapping. Essentially you would change your Fund model to something like this:
Ext.define('Fund', {
extend: 'Ext.data.Model',
fields: [
{ name: 'catname', type: 'string' },
{ name: 'cat_id', type: 'int' },
{ name: 'region_name', type: 'string',
mapping: 'region.region_name'},
{ name: 'region_id', type: 'int',
mapping: 'region.region_id'}
]
....
});
You see what we did there? We flattened the Region data into the Fund record. And now your store will have no problems accessing Region name data by name.
Good Luck,
Dmitry.