Antd table is not updating on dataSource updates/changes - antd

<Table
columns={columnsStructure}
dataSource={source}
pagination={pagination}
onChange={handleChange}
/>
the source is an array of objects. On component mount Table is rendering properly but once datSource i.e. source is updated, table rows remain the same.
How to resolve this issue. Wanted to update ant design table on source update.

To resolve this Ant-Design table data auto-update issue, you have to pass the data-source value as a clone of the observable value. like
<Table
columns={columnsStructure}
dataSource={[...source]}
pagination={pagination}
onChange={handleChange}
/>

The above solution did not work for me. I found that since the 'key' property of the row objects is remaining the same, React was not picking up the change.
What worked for me, though a bit hacky is generating a random key when a row object is changed. Hopefully the key is not being used for anything other than React to keep track of it, which is what it's usually meant for.
const updatedEntry = {
...record,
key: (Math.random() + 1).toString(36).substring(7),
//anyproperty : //yourValue
}
Still looking for more cleaner solutions to this problem.

This is a trap of shallow comparison.
If you reused the objects in the oldDataSource to increase efficiency, like:
const newDataSource=[...oldDataSource]
newDataSource[0].column1="newValue"
setDatasource(newDataSource)
This will not work.
Yes, the table is updating, because you have a new list. However, the list components inside the table are not updating, because they see the old objects (although you changed the value).
To make it work you need to do:
const newDataSource=[...oldDataSource]
newDataSource[0]={...newDataSource[0], column1: "newValue"}
setDatasource(newDataSource)
Then that row will update.

To resolve this Ant-Design table data auto-update issue, you have to pass the data-source value as a clone of the observable value. like
var _ = require('lodash');
...
<Table
columns={columnsStructure}
dataSource={_.cloneDeep(sources)}
pagination={pagination}
onChange={handleChange}
/>

Add render in columns
{
title: "amount",
dataIndex: "amount",
key: "amount",
render: (amount) => (amount),
}

Related

Phalcon Save: Can I update only specified columns if update?

I have a table with this columns:
param_id
val_value
val_flag
date_value
tmp_value
tmp_flag
And I have an array of elements, I always have param_id and date_value, but sometimes i have val columns and other times I have tmp columns.
I use $data->save() because sometimes I need to create a new register in db and other times I need to update the register with param_id and date_value.
The question is: Is there any way to do an insert/update but when is an update, only update tmp columns or val columns? I think a find First is my only option, but maybe there is another way.
Thank you.
[EDIT]
I'm trying with the whitelist but it does not work. Let me explain how the method works: I get a request to a web service, process the xml and generate an array of elements with the information collected, after processing these elements I have an array of elements of the class appropriate to save, but these may be new or existing and may contain tmp or val values, I have tried with this but I still change the values to null.
if ($medida->tipo == 'temporal'){
$whiteList = array('val_value','val_flag');
}else if ($medida->tipo == 'validado'){
$whiteList = array('tmp_value','tmp_flag');
}
$dato->save(null, $whitelist);
I do not have data of the post, I use null instead, I have also tried to use an array with the manual assignment of the data obtaining the same result.
Here are two options that can help you:
1) Use 'whitelist' for the save() method.
$obj->save($this->request->getPost(), ['tmp_1', 'tmp_2']);
More info in the documentation.
2) Use the 'Event Manager'.
The methods beforeCreate() and beforeUpdate() will be useful so you can decide which fields to use.
More info in the documentation.
Also if you really want phalcon phql to update only columns which changed you need to enable dynamic update.

Big Commerce Custom Fields

I'm planning on allowing a client to provide a couple codes for each product that I'll need to reference with Javascript on the product pages.
Basically my plan was to use the Big Commerce's 'custom fields' to do so, but I'm having trouble spitting out the custom fields onto the product pages. I've been looking all over for some type of GLOBAL variable that allows me to reference custom fields, but I'm coming up dry. I would think there would be some type of GLOBAL array with all the custom fields in it, or a way to reference them by name directly.
Am I blind, or is there just no way to do this directly in the BC template file?
Thanks.
In Bigcommerce the custom fields can generally be found within the ProductOtherDetails.html Panel which contains a Snippet named ProductCustomFieldItem.html. This snippet has the markup for each custom field that the system outputs.
Inside of the ProductCustomFieldItem.html Snippet are the two codes you are looking for: %%GLOBAL_CustomFieldName%% and %%GLOBAL_CustomFieldValue%%.
I ran into this as well - given that it's quite a long time later, I'm supposing there's no better answer - a decent amount of searching turned up nothing useful as it seems all you can do is output the full set of custom fields as a set of divs.
So, I output them into a div which was hidden:
<div id="fpd-custom-fields" style="display:none;">
%%SNIPPET_ProductCustomFields%%
</div>
and then set up a javascript function to get the value based on the name:
function getCustomFieldValue(label)
{
var value = '';
$('#fpd-custom-fields div.Label').each(function()
{
if($(this).text().toLowerCase() == (label.toLowerCase() + ':'))
{
value = $('div.Value', $(this).parent()).text().trim();
}
});
return value;
}
Doesn't feel quite right as it's not a very clean solution, but was the best I could come up with unfortunately!

grails: how to properly edit/update a collection?

I just wasted half a day trying to figure this out, reading about some workarounds, and thinking "it can't be that bad - there must be a straightforward to do edit a collection in Grails, whethere using scaffolded views or my own."
Let's say I have this domain object:
class TreeGroup {
String name
List<Tree> trees
static hasMany = ['trees': MyTree]
}
Just to explain the choice of data structure - I need my records to be unique, but in the order I set. That's why I chose List, AFAIK one cannot rely on order in a Set. So there are 2 pieces to this question - 1) how to remove from any Collection, for example a Set, 2) is List the best replacement for Set in this context (preserving order).
I want to be able to create a group record with no trees in it and make 4 updates:
edit/save
edit the group record to reference 2 trees A and B
add another tree C
remove A
remove B and C
And obviously, I want the desired state after every step. Currently though, I can only add records, and if I even edit/save to list, the list elements are added to it again.
I am using the multiple select tag for this. It looks like this:
<g:select name="trees" from="${allTrees}" optionKey="id"
multiple="true" class="many-to-many"
value="${trees ? trees*.id : treeGroupInstance?.trees*.id}" />
and that's fine, in the sense that it generates an HTTP header with these variables on update:
_method:PUT
version:19
name:d5
trees:1
_action_update:Update
But the data binder only adds new elements, it never lets you edit a list.
What is the cleanest way to do it ? Is it me, not reading something obvious, or is this a design flaw of grails data binding (and of so, when/how will it be fixed) ?
Is there a way perhaps via a hidden HTTP parameter to clear the list before (re)adding elements ?
Thanks
I ended up doing this:
private repopulate(def domainObject, String propertyName, Class domainKlaz) {
if (params[propertyName] != null) {
domainObject[propertyName].clear()
domainObject[propertyName].addAll(
params[propertyName].collect { domainKlaz.get(it) }
)
}
}
and I am calling it in update controller method before save(), for every collection. OMG how ugly.

Vaadin table row change best practice

What is the best way to replace a table row in Vaadin (6 and 7)? I use BeanItemContainer. The bean is an entity and has changed (not the ID).
I think this cause unnecessary method invocation and/or object creation:
table.removeItem( item );
table.addItem( item );
As I know, the best pratice is:
BeanItemContainer<DataModel> tableDataSource = new BeanItemContainer<>(DataModel.class);
table.setContainerDataSource(tableDataSource);
When you want to replace a row, just replace the data of this row in tableDataSource:
tableDataSource.removeItem(item);
tableDataSource.addItem(item);
The difference between your code and mine is:
In your code, you replace the row (it means the row is removed from the table and then a new row will be added to table).
In my example, I just replace the data of row.
Hope it helps

How can I attach some data to a row in a tableView - Corona SDK

I have a tableView, and I am adding rows to it from different sources. Using the original widget library I was able to attach data to the insertRow method, but since upgrading to 2.0 that now seems impossible.
How I think I should be able to attach data:
list:insertRow{
rowHeight=rowHeight,
isCategory=isCategory,
rowColor=rowColor,
lineColor=lineColor,
data=data[i]
}
data should then be accessible inside the touch event:
local function onRowTouch( event )
print( event.target.data )
end
Since widget2.0 this is not the case. My question is this: how can I access that data?
NB: In other parts of the app I have been able to reference the original data table by using the row index as the table key, eg: print( data[event.row.index] ), but I cannot do this on a table with multiple data sources.
I have found an undocumented way of passing data to the table row. I'm placing it here in case anyone finds this thread who is having the same issue. As it is undocumented it may be liable to change at any point.
You can attach data using the following:
list._view._rows[#list._view._rows].data = data
data can be anything, and this works in the same way as adding it into the insertRow method.
To access this data in the touch method it would simply be: event.target.data
The way you do this is to use the index value on the row and inside the onRowRender function you reference your data table:
local function onRowRender(event)
id = event.index
print(data[id])
end
list:insertRow{
rowHeight=rowHeight,
isCategory=isCategory,
rowColor=rowColor,
lineColor=lineColor,
}
With the index value you can fetch whatever you need from your data.

Resources