I am not able to update record in localStorage by id. I get the exception :
Uncaught TypeError: Cannot read property 'type' of undefined WebStorage.js:391Ext.define.getIds WebStorage.js:391Ext.define.update WebStorage.js:190Ext.define.runOperation Batch.js?_dc=1423751003307:251Ext.define.start Batch.js?_dc=1423751003307:178Ext.define.batch Proxy.js?_dc=1423751002203:456Ext.define.sync AbstractStore.js?_dc=1423751002173:810Ext.define.afterEdit AbstractStore.js?_dc=1423751002173:906Ext.define.callStore Model.js?_dc=1423751003310:1814Ext.define.afterEdit Model.js?_dc=1423751003310:1773Ext.define.set Model.js?_dc=1423751003310:1175(anonymous function) Main.js?_dc=1423751002786:26(anonymous function) VM3763:6wrap
My model is simple:
Ext.define('AM.model.Points', {
extend: 'Ext.data.Model',
idProperty: {
name: 'UUID',
type: String,
isUnique: true
},
fields: [
{
name: 'NO',
type: "string"
},
{
name: 'Y',
type: "int"
},
{
name: 'ROW',
type: 'int'
},
{
name: 'SEAT',
type: 'string'
},
{
name: 'PROCEEDED',
type: 'int'
},
{
name: 'X',
type: "int"
},
{
name: "CurrentPlace",
type: "int",
defaultValue: 0
}
],
});
My controller class init function:
init: function(){
// метод getStore контроллера возвращает экземпляр хранилища,
// если он уже создан - или создаёт его
console.log('Main controller init function()');
var changingImage = Ext.create('Ext.Img', {
src: '/is-bin/intershop.static/WFS/EnterpriseOrg-MainChannel-Site/ProductStore/ru_RU/kzch.jpg',
renderTo: Ext.get('canv1')
});
Ext.get('canv1').on('click', function(eventObj, elRef) {
var index = Ext.StoreMgr.lookup("LocalStore").findExact('UUID',AM.util.Utilities.CurrentPlace);
var rec = Ext.StoreMgr.lookup("LocalStore").getAt(index);
console.log('Ext.StoreMgr.lookup("LocalStore") ' + Ext.StoreMgr.lookup("LocalStore"));
console.log('index' + index);
console.log('rec' + rec);
var uuid = rec.get('UUID');
console.log('uuid is: '+uuid);
**rec.set('X', window.event.offsetX);**
});
The logic is that I click on canvas and pass X coordinate of the click to method on click. I retrieve model from store by previously saved id to update it. But I cant update record. What should be done? Version 4.2.1 Thanx in advance.
Related
Using Ext JS 7.1 Modern, I have prepared an example to show the problem.
When I have remote filters on my main store, binding the dataview.List to a ChainedStore correctly handles my local filtering. However, when I also add a PullRefresh plugin to the list, I get an error during pull refresh. I see from the source code that the plugin doesn't consider the possibility that a list's store can be a ChainedStore.
I have tried to explain the problem with a Sencha Fiddle and also attached the code below.
I have temporarily solved the problem by overriding the fetchLatest and onLatestFetched methods of Ext.dataview.pullrefresh.PullRefresh plugin, to use the source store if the list's store is a ChainedStore. But I believe the source code must be updated to handle this case.
app.js
Ext.define('App.model.Test', {
extend: 'Ext.data.Model',
fields: ['id', 'firstName', 'lastName']
});
Ext.define('App.store.Test', {
extend: 'Ext.data.Store',
alias: 'store.teststore',
model: 'App.model.Test'
});
Ext.define('App.viewmodel.Test', {
extend: 'Ext.app.ViewModel',
alias: 'viewmodel.test',
data: {
query: ''
},
stores: {
test: {
type: 'teststore',
autoLoad: true,
proxy: {
type: 'ajax',
url: 'names.json',
reader: {
type: 'json',
rootProperty: 'data'
}
},
remoteFilter: true,
filters: {
property: 'id',
value: 1
}
},
chained: {
type: 'chained',
autoLoad: true,
source: '{test}'
}
}
});
Ext.define('App.controller.TestController', {
extend: 'Ext.app.ViewController',
alias: 'controller.testcontroller',
doSearch: function (field) {
var list = this.lookup('list'),
store = list.getStore(),
value = field.getValue();
if (Ext.isEmpty(value)) {
store.removeFilter('firstName')
} else {
store.filter([{
property: 'firstName',
value: value,
operator: 'like'
}])
}
}
});
Ext.define('App.dataview.TestList', {
extend: 'Ext.dataview.List',
xtype: 'testlist',
viewModel: {
type: 'test'
},
plugins: [{
type: 'pullrefresh',
mergeData: false
}],
emptyText: 'Name not found',
bind: {
store: '{chained}'
},
itemTpl: '<div class="contact">{id} <b>{firstName} {lastName}</b></div>'
});
Ext.define('App.MainView', {
extend: 'Ext.Panel',
controller: 'testcontroller',
fullscreen: true,
viewModel: {
type: 'test'
},
items: [{
xtype: 'searchfield',
ui: 'solo',
placeholder: 'Search names',
listeners: {
buffer: 500,
change: 'doSearch'
},
bind: {
value: '{query}'
}
}, {
reference: 'list',
xtype: 'testlist'
}]
})
Ext.application({
name: 'App',
mainView: 'App.MainView'
});
names.json
var data = [{
id: 1,
firstName: 'Peter',
lastName: 'Venkman'
}, {
id: 2,
firstName: 'Raymond',
lastName: 'Stantz'
}, {
id: 3,
firstName: 'Egon',
lastName: 'Spengler'
}, {
id: 4,
firstName: 'Winston',
lastName: 'Zeddemore'
}]
var results = data.filter(function(record) {
if (params.filter) {
return record.id > params.filter[0].value
}
})
return {
"success": true,
"data": results
}
App.override.dataview.pullrefresh.PullRefresh:
Ext.define('App.override.dataview.pullrefresh.PullRefresh', {
override: 'Ext.dataview.pullrefresh.PullRefresh',
privates: {
fetchLatest: function() {
const store = this.getStore().isChainedStore ? this.getStore().getSource() : this.getStore()
store.fetch({
page: 1,
start: 0,
callback: this.onLatestFetched,
scope: this
});
},
onLatestFetched: function(newRecords, operation, success) {
var me = this,
list = me.getList(),
store = list.getStore().isChainedStore ? list.getStore().getSource() : list.getStore(),
length, toInsert,
oldRecords, newRecord, oldRecord, i;
if (success) {
if (me.getMergeData()) {
oldRecords = store.getData();
toInsert = [];
length = newRecords.length;
for (i = 0; i < length; i++) {
newRecord = newRecords[i];
oldRecord = oldRecords.getByKey(newRecord.getId());
if (oldRecord) {
oldRecord.set(newRecord.getData());
}
else {
toInsert.push(newRecord);
}
}
store.insert(0, toInsert);
}
else {
store.loadRecords(newRecords);
}
me.setLastUpdated(new Date());
}
me.setState('loaded');
list.fireEvent('latestfetched', me, toInsert || newRecords);
if (me.getAutoSnapBack()) {
me.snapBack(true);
}
}
}
})
Thanks in advance
Since this post, instead of being a question, was a bug report with a possible solution, it has been posted to Ext JS 7.x Community Forums\Ext JS 7.x Bugs.
The above solution, that overwrites the plugin where source store is needed, works if anyone comes across the same issue.
I have tried to refresh the Grid every 5 or 10 seconds which is using REST Proxy, but the grid is not getting refreshed more than once. Please find the code which we have tried.
Ext.define('App.Store.DeviceStore', {
extend: 'Ext.data.Store',
requires: [
'Ext.data.proxy.Ajax',
'Ext.data.reader.Json'
],
constructor: function(cfg) {
var me = this;
cfg = cfg || {};
me.callParent([Ext.apply({
storeId: 'app.store.DeviceStore',
model: 'App.model.DeviceModel',
activeRefreshTask:false,
pageSize: 5,
autoLoad: {
pageSize: 5
}
}, cfg)]);
},listeners:{
'load':function(store,records,successful,operation){
if(successful === true && store.activeRefreshTask === false){
var task = {
identifyId: 'deviceListStore',
run: function() {
if (App.app._currentPage == 'devicesform') {
store.reload();
} else {
Ext.TaskManager.stop(this);
}
},
interval: '10000'
}
Ext.TaskManager.start(task);
store.activeRefreshTask = true;
}
}
}
});
The model for the above store is
Ext.define('App.model.DeviceModel', {
extend: 'Ext.data.Model',
requires: [
'Ext.data.field.String'
],
proxy:{
type:'rest',
reader: {
type: 'json',
rootProperty: 'data',
totalProperty:'total'
},
useDefaultXhrHeader: false,
headers:{'Content-Type':'application/json'},
api: {
read: 'url given gere'
}
},
fields: [
{
type: 'string',
name: 'id'
},
{
type: 'string',
name: 'name'
},
{
type: 'string',
name: 'desc'
},
{
type: 'string',
name: 'ipAddr'
}
]
});
I have found the issue , You have passed the interval as string in place lo number.
just change to interval: '10000' to inteval: 10000 and your taskrunner will runs fine.
var runner = new Ext.util.TaskRunner(),
updateStore , task;
updateStore = function() {
if (App.app._currentPage == 'devicesform') {
store.load();
} else {
Ext.TaskManager.stop(this);
}
};
task = runner.start({
run: updateStore ,
interval: 1000
});
probably your store.reload is sending again the same params on the request, so with a request that not change nothing changes.
I am trying to save data to local storage and I want to use my own ID.
But new id is generated.. and not using my ID.
My model:
Ext.define('mOQOLD.model.ActivityList',{
extend:'Ext.data.Model',
config:{
dProperty : 'uniqueid', // dummy name(not a field)
clientIdProperty : 'ID',
identifier: {
type: 'simple'
},
fields: [
{ name: "ID", type: "auto" },
{ name: "activityID", type: "int" },
{ name: "newRandom", type: "float" },
{ name: "rTime", type: "date", dateFormat: "Y-m-d H:i:s" }
]
}
});
My store:
Ext.define('mOQOLD.store.ActivityListStoreOffline',{
extend:'Ext.data.Store',
requires:["mOQOLD.model.ActivityList",
'Ext.data.proxy.LocalStorage'],
config:{
storeId:"ActivityListStoreOffline",
model:"mOQOLD.model.ActivityList",
grouper: {
groupFn: function(rec) {
var date = rec.get("actDtlStime");
return Ext.Date.format(date, "h a");
}
},
autoLoad:false,
sorters: [
{ property: "actDtlStime", direction: "ASC" }
],
proxy : {
type : 'localstorage',
id : "ActivityListStoreOffline",
model : "mOQOLD.model.ActivityList",
reader: {
type: "json"
}
}
}
})
The result( chrome) :
key : ActivityListStoreOffline-ext-record-19
value:
{"ID":"153",15:13:00","activityID":111,"newRandom":null,"rTime":"2015-05-26 19:31:51","id":"ext-record-19"}
What I expect:
key : ActivityListStoreOffline-153
value:
{"ID":"153",15:13:00","activityID":111,"newRandom":null,"rTime":"2015-05-26 19:31:51"} no id generated!!!
Thanks in advance..
There are two places you can set the ID:
In the model(http://docs.sencha.com/extjs/4.1.3/#!/api/Ext.data.Model-cfg-idProperty)
and in the reader (http://docs.sencha.com/extjs/4.1.3/#!/api/Ext.data.reader.Reader-cfg-idProperty)
Both places use the "idProperty" attribute. Which defaults to lowercase 'id'.
For example, change your reader to:
proxy : {
type : 'localstorage',
id : "ActivityListStoreOffline",
model : "mOQOLD.model.ActivityList",
reader: {
type: "json",
idProperty: "ID",
}
}
My Model
config:{
fields: [
{ name: 'AcctManagFirst', type: 'string' },
{ name: 'AcctManagLast', type: 'string' },
{ name: 'Name', type: 'string' },
{ name: 'Terms', type: 'string' },
{ name: 'Freight', type: 'string' },
{ name: 'Taxable', type: 'string' },
{ name: 'Taxtable', type: 'string' },
{ name: 'TaxTableRate', type: 'string' },
{ name: 'BillToAddr', type: 'string' },
{ name: 'BCity', type: 'string' },
{ name: 'BState', type: 'string'},
{ name: 'BZip', type: 'string' },
{ name: 'WHAddr', type: 'string' },
{ name: 'WHCity', type: 'string' },
{ name: 'WHState', type: 'string' },
{ name: 'WHZip', type: 'string' },
and my store
config:{
model: 'Sample.model.User',
proxy:
{
type: 'jsonp',
url: 'http://xxx.xxx.com/customer_info.php',
buildUrl : function (request) {
var url = this.getUrl(request),
params = request.getParams() || {};
url = url + params.CustNo;
request.setUrl(url);
return this.callParent([request]);
},
reader: {
type: 'json',
rootProperty: 'content'
}
}
I will get the user data from the store... how to write a view that display data with respect to the user.. user data changes .. now I can write the static data but I need the data to be dynamic..
Firstly, your question is awfully vague and difficult to answer.
I think what you're trying to accomplish is to have a list populated dynamically from your store which when tapped will display a detail view.
You'll need to put together a list view to display your data as well as a container for the detail view.
You will also need a controller with a reference to both views and a control on the list view's itemtap event. The method called from that control should set the data into your detail view then push that view onto the Viewport.
I can be more specific but as I mentioned this question is too vague to put together any kind of example for you. Adding a hardcoded set of data to your store would help, as well as full class examples of your views, stores, controllers and models.
I'm defining a store and I want to dynamically assign a Model for it at creation. So if I create my DropDownStore and I don't pass a model config with it it needs to rely on the default model(DropDownModel).
Here is my DropDownModel + DropDownStore:
Ext.define('DropDownModel', {
extend: 'Ext.data.Model',
fields: [
{ name: 'Id', type: 'int' },
{ name: 'Name', type: 'string' }
]
});
Ext.define('DropDownStore', {
extend: Ext.data.Store,
proxy: {
type: 'ajax',
actionMethods: { read: 'POST' },
reader: {
type: 'json',
root: 'data'
}
},
constructor: function(config) {
var me = this;
if (config.listUrl) {
me.proxy.url = config.listUrl;
}
me.model = (config.model) ? config.model : 'DropDownModel'; //This line creates some weird behaviour
me.callParent();
//If the URL is present, load() the store.
if (me.proxy.url) {
me.load();
}
}
});
This is a creation of the DropDownStore with a dynamic model:
Ext.define('RelationModel', {
extend: 'Ext.data.Model',
fields: [
{ name: 'Id', type: 'int' },
{ name: 'RelationName', type: 'string' },
{ name: 'RelationOppositeName', type: 'string' }
]
});
...//a random combobox
store: Ext.create('DropDownStore', {
listUrl: 'someprivateurl',
model: 'RelationModel'
})
...
When I edit the line in the constructor method to
me.model = (config.model) ? config.model : undefined
It works like expected for the dynamic model but not anymore for the default models.
If I let it be
me.model = (config.model) ? config.model : 'DropDownModel';
It works for the default models and not for the dynamic model.
How can I assign a model to a store at creation?
constructor: function(config) {
var me = this;
if (config.listUrl) {
me.proxy.url = config.listUrl;
}
me.callParent();
if (config.extraFields) {
me.model.setFields(config.extraFields);
}
//If the URL is present, load() the store.
if (me.proxy.url) {
me.load();
}
}
store: Ext.create('DropDownStore', {
listUrl: 'someprivateurl',
extraFields: [
{ name: 'Id', type: 'int' },
{ name: 'RelationName', type: 'string' },
{ name: 'RelationOppositeName', type: 'string' }
]
}),