Let's say I have a big list of items where the user can go and favourite items as they wish. These favourites then go to a new node userLikedItems/userUID/.
When saving favourites, I am trying to figure out the best way to do so:
Here is my current, duplicative approach:
//duplicating all the data when a user favourites an item into their own node under userLikedItems
{
"hwUjzftGyCgMrRgNv4Djg5F4ZCQ2" : {
"24K Carrot" : {
"effects" : {
"Euphoria" : true,
"Happy" : true,
"Relaxing" : true,
"Sleepy" : true
},
"medical" : {
"Arthritis" : true,
"Bipolar Disorder" : true,
"Chronic Pain" : true,
"Depression" : true,
"Fatigue" : true,
"Inflammation" : true,
"Insomnia" : true,
"Loss of Appetite" : true,
"Migraines" : true,
"PTSD" : true,
"Stress" : true
},
"levels" : "18% - 24%",
"title" : "24K Carrot",
"titleLowercase" : "24k Carrot",
"uid" : "24K Carrot"
},
"2 Pac" : {
"effects" : {
"Cerebral" : true,
"Focus" : true,
"Happy" : true,
"Horny" : true,
"Relaxing" : true,
"Uplifting" : true
},
"medical" : {
"Arthritis" : true,
"Cramps" : true,
"Depression" : true,
"Gastrointestinal Disorder" : true,
"Loss of Appetite" : true,
"Migraines" : true
},
"levels" : "29%",
"title" : "2 Pac",
"titleLowercase" : "2 pac",
"uid" : "2 Pac"
},
}
}
Here is the next approach where I am trying to determine if it is a better practice than my current approach:
//data stored with only uid:true under user's favourites node
{
"hwUjzftGyCgMrRgNv4Djg5F4ZCQ2" : {
"24K Carrot" : true,
"2 Pac" : true,
"Triple Take" : true,
}
// fetching the rest of the data inside list item
componentDidMount() {
firebase.database().ref('/userLikedItems').child(this.props.user.item.uid).once('value', snapshot => {
const itemData = snapshot.val();
this.setState({
name: itemData.name,
image: itemData.image,
type: itemData.type
});
});
}
So basically when a list item is mounted I am calling this query to fetch the rest of the data. I am worried this is a bad practice.
Right now I am currently duplicating all the item data in the userLikedItems node which means I would not have to perform that query for every item, instead I would simply load all the data from the users node - the problem with this is I have to use a cloud function to keep the data consistent when the main item changes and there is a lot of duplicate data in my database when it could instead just be a simple boolean for each item.
I appreciate all the feedback!
Cheers.
Related
Below is the JSON i received from server.
Now i am having variable public checkId: any = 54
How to extract data corresponding to ID = 54 from below JSON ??
I want to extract below that is mentioned against KEY 54
"Increase Again": true,
"Decrease Previous" : true,
"Like" : true,
"Dislike" : true,
"Old Again" : false,
"Others" : true
Below is the JSON from which i have to extract above data
{
"27" : {
"Increase": true,
"Decrease" : true,
"Like" : true,
"Dislike" : true,
"Old" : false,
"Others" : true
},
"54" : {
"Increase Again": true,
"Decrease Previous" : true,
"Like" : true,
"Dislike" : true,
"Old Again" : false,
"Others" : true
},
"104" : {
"Increase Previous": true,
"Decrease Prior" : true,
"Like" : true,
"Dislike" : true,
"Old" : false,
"Others Check" : true
}
}
Thanks in advance ...
#Edit - The key are not simply 1,2,3 they are specific Id 53,54,55 also it can 100, 108, 4657
You can simply get the specific element by passing the checkId in your response, For instance I'm assuming that you have that JSON in result variable.
You can call it in the following way
let result = //Your json;
let checkId = 2;
result[checkId] ==> This will return 2nd object of JSON
You Can get Ur Desired Value simply like this..
let checkId = 2;
let data = {
"1": {
"Increase": true,
"Decrease": true,
"Like": true,
"Dislike": true,
"Old": false,
"Others": true
},
"2": {
"Increase Again": true,
"Decrease Previous": true,
"Like": true,
"Dislike": true,
"Old Again": false,
"Others": true
},
"3": {
"Increase Previous": true,
"Decrease Prior": true,
"Like": true,
"Dislike": true,
"Old": false,
"Others Check": true
}
}
let result = data[checkId]
console.log(result)
Good morning. I made a data search & filter with datatables and it worked .. but when I moved the page and returned to that page the data was still stuck (not reset). In view I made it like the following image:
and in the js file I made it like this
brandmanage = $('#brandmanage').DataTable({
dom : 'rtpi',
pageLength: {{ $limit ?? '10' }},
language : {
paginate : {
previous : '<i class="fa fa-angle-left"></i>', // or '←'
next : '<i class="fa fa-angle-right"></i>', // or '→'
},
},
processing : true,
drawCallback : function( settings ) {
$('#lengthInput option[value={{ $limit ?? '10' }}]').attr('selected','selected');
},
serverSide : true,
stateSave : true,
ajax : {
url : "{{ route('lms.brand.getdata',['pfx'=>$pfx]) }}",
dataType : "json",
type : "POST",
data : { _token: "{{csrf_token()}}" }
},
columns : [
{ data : "brand" },
{ data : "corporate" },
{ data : "num_of_company" },
{ data : "primary" },
{ data : "secondary" },
{ data : "status" },
{ data : "action",
orderable : false,
className : "text-center",
},
],
});
$('#brandDataLength').on('change', function () {
brandmanage.page.len( $(this).val() ).draw();
});
$('#searchBrand').on('keyup', function () {
brandmanage.search( this.value ).draw();
});
What do I do so that when I have moved pages, the search results can be reset?
If you change stateSave to false, then dataTables will not remember the selected filters etc. Thereby the search results will be reset when you reload the page.
I've got some code that, when switching which row is selected, it triggers a save of the previously selected row.
The row is being successfully saved without any problem, however the successfunc isn't being called at all - my console.log output never shows up, and the code in this function isn't being run. I also tried specifying the function as the aftersavefunc, but couldn't get that to work either.
Seems like a simple syntax problem, but I can't quite get it right. Am I not specifying this function properly?
As a side note, I realize that reloading the entire grid after a row save seems like overkill, but in the context of where this particular piece of code is, within the larger structure of my app, this snippet of code is a special case.
The full jqGrid code is:
var lastSelectedMainGridRowID = 0;
var lastSelectedSubGridRowID = 0;
var translationsFeed = "/update/translations/ajax/translations_feed.php";
var translationsEdit = "/update/translations/ajax/translations_edit.php";
var translationsSubGridFeed = "ajax/translations_subgrid_feed.php";
var translationsSubGridFeedEdit = "ajax/translations_subgrid_feed_edit.php";
$(document).ready(function () {
$("#translationsList").jqGrid({
caption : "Translations",
datatype : "xml",
url : translationsFeed,
editurl : translationsEdit,
mtype : "get",
pager : "#translationsPager",
rowNum : 20,
autowidth : true,
sortname : "phrase",
sortorder : "asc",
viewrecords : true,
multiselect : false,
hidegrid : false,
height : 300,
altRows : true,
rownumbers : true,
toolbar : [false],
loadComplete: function(data) {
jQuery("#translationsList").setSelection (0, true);
},
colNames : ["phrase_id", "translation_id", "language_cd", "Phrase", "Translation", "Modified", "Created", "Active"],
colModel : [
{ name : "phrase_id", index : "phrase_id", sortable : true, search : false, editable: true, edittype : "text", editrules: { edithidden: true }, hidden: true},
{ name : "translation_id", index : "translation_id", sortable : false, search : false, editable: true, edittype : "text", editrules: { edithidden: true }, hidden: true},
{ name : "language_cd", index : "language_cd", sortable : true, search : true, editable: true, edittype : "text", editrules: { edithidden: true, required : true }, hidden: true },
{ name : "Phrase", width:200, index : "phrase", sortable : true, search : true, editable: true, edittype : "text", editrules: { required: true } },
{ name : "Translation", width:200, index : "translation", sortable : true, search : true, editable: true, edittype : "text", editrules: { required: false } },
{ name : "Modified", width:100, index : "modify_dt", sortable : true, search : true },
{ name : "Created", width:100, index : "create_dt", sortable : true, search : true },
{ name : "Active", width:20, index : "active", sortable : true, search : true, editable: true, edittype: "checkbox", editoptions: {value:"Yes:No", checked: true} }
],
onSelectRow: function(id) {
jQuery('#translationsList').jqGrid('saveRow', lastSelectedMainGridRowID);
jQuery('#translationsList').jqGrid('editRow', id, true);
lastSelectedMainGridRowID = id;
},
subGrid: true,
subGridRowExpanded: function(subgrid_id, row_id) {
var subgrid_table_id;
jQuery("#"+subgrid_id).html("<table id='"+subgrid_table_id+"' class='scroll'></table>");
jQuery("#"+subgrid_table_id).jqGrid({
url: translationsSubGridFeed + "?phrase_id=" + row_id,
editurl: translationsSubGridFeedEdit,
datatype: "xml",
colNames: ['phrase_id', 'translation_id', 'language_cd', 'Translations', 'Language', 'Active'],
colModel: [
{name:"phrase_id", index:"phrase_id", sortable: false, editable: true, edittype : "text", editrules: { edithidden :true }, hidden: true},
{name:"translation_id", index:"translation_id", sortable: false, editable: true, edittype : "text", editrules: { edithidden :true }, hidden: true},
{name:"language_cd", index:"language_cd", sortable: false, editable: true, edittype : "text", editrules: { edithidden :true }, hidden: true},
{name:"Translation", index:"translation", sortable: true, editable: true, edittype:"text", width:589},
{name:"Language", index:"language_disp", sortable: true, editable: false, width:250},
{name:"Active", index:"active", sortable: true, editable: true, edittype:"checkbox", editoptions:{value:"Yes:No", checked: true}, width:80}
],
height: "100%",
rowNum:20,
sortname: 'language_cd',
sortorder: "asc",
onSelectRow: function(id) {
jQuery("#"+subgrid_table_id).jqGrid('saveRow', lastSelectedSubGridRowID, function(response) {
console.log("Data: " + response.responseText);
return false;
});
jQuery("#"+subgrid_table_id).jqGrid('editRow', id, true);
lastSelectedSubGridRowID = id;
}
});
}
});
Perhaps I don't need to use saveRow. In this case, what I'm doing is:
When you click on a row, it becomes editable
If you then click on a second row, the first row is saved (and no longer selected), and the new second row then becomes editable. Similar to saving a row "onBlur", so to speak.
I don't see the place of code where responseData variable are defined. The code responseData[0] should throw an exception, so the console.log("Data: " + responseData[0]); will not display any data. The line of code should be probably fixed as
console.log("Server response: " + result.responseText);
UPDATED: Without having the data for the both grid and for example the subgrid corresponds the first row one can't debug the code. Reading is not so effective. If you posted the test data (two XML files) I could try to localize the problem.
An important error is that you only declare subgrid_table_id variable, but not assign a value for it. Typically one construct an unique id name subgrid_table_id based on the subgrid_id. For example
var subgrid_table_id = subgrid_id+"_t";
instead of var subgrid_table_id; only.
Nevertheless some things I find a little suspected:
I don't understand why you return return false; from the successfunc. It means that you interpret the server response as an error and the normal actions on successful server response should be interrupted. I would recommend you additionally use errorfunc parameter of saveRow. In my server code the server always return error HTML status code in case of the server error. So I never need use successfunc and use aftersavefunc and errorfunc only.
The subgrid has many column which already exist in the corresponding row of the parent grid. The potential problems here are not only spending of additional memory. You don't posted the grid data and so I don't know what values you use as rowids for grids. It is very important to have no id duplicates on the HTML page. So you should be careful in the subject. Why you need ? Probably you can just use extraparam parameter of saveRow and editRow instead of the usage of phrase_id, translation_id and language_cd hidden columns having editable: true, editrules: { edithidden :true }, hidden: true properties?
Here is my code, its supposed to prevent node copy when using ctrl key, but it still allows copy and doesn't prevent it.
I use "copy_modifier" : false as per the documentation - any idea why it doesn't work?
I am using the stable version "jsTree 1.0-rc3" downloaded via the big download button on the website only a few days ago.
$(function () {
$("#jsTree")
.jstree({
"plugins" : ["themes","html_data","ui","crrm","hotkeys","types","dnd","contextmenu"], contextmenu: {items: customMenu}
//"core" : { "initially_open" : [ "node_root" ] }
,"types" : {
"valid_children" : [ "group","unknowngroup" ],
"types" : {
"group" : {
"valid_children" : ["event"],
"start_drag" : false,
"move_node" : false,
"delete_node" : false,
"remove" : false,
"icon" : {
"image" : "layout/img/folder.png"
},
},
"unknowngroup" : {
"valid_children" : ["event"],
"start_drag" : false,
"move_node" : false,
"delete_node" : false,
"remove" : false,
"icon" : {
"image" : "http://www.veryicon.com/icon/16/System/Pleasant/Recycle%20Bin%20e.png"
},
},
"event" : {
"valid_children" : "none",
"icon" : {
"image" : "http://ouccc.objectis.net/events/aggregator/previous/event_icon.gif"
},
"start_drag" : true,
"move_node" : true,
"delete_node" : false,
"remove" : false
}
},
"dnd" : {
"copy_modifier" : false,
"drag_check" : function (data) {
return {
after : true ,
before : true ,
inside : true
};
}
}
}
}).bind("rename.jstree", function (e, data) {
if(prefix!="")
{
commitGroupRename(data.rslt.obj.attr("id").substring(11),data.rslt.new_name);
var text= prefix + data.rslt.new_name;
$("#jsTree").jstree('rename_node', data.rslt.obj, text );
prefix="";
}
}).bind("loaded.jstree", function (event, data) {
//$("#jsTree").jstree("open_all");
}).bind("dblclick.jstree", function (event) {
var node = $(event.target).closest("li");
//var data = node.data("jstree");
if ($(node).attr('rel')=="group" && prefix =='')
{
var text = $("#jsTree").jstree('get_text',node);
prefix = text.substring(0,5);
text = text.substring(5);
$("#jsTree").jstree("rename_node", node , text );
$("#jsTree").jstree("rename",node);
}
}).bind("select_node.jstree", function (node, ref_node) {
var theRealNode = $.jstree._focused().get_selected();
if (theRealNode.attr('rel')=="group")
{
$('#btnRenameSelected').attr("disabled", false);
$('#btnRenameSelected').removeClass("ui-state-disabled");
}
else
{
$('#btnRenameSelected').attr("disabled", true);
$('#btnRenameSelected').addClass("ui-state-disabled");
}
});
});
Fixed - as you can see "dnd" is actually inside "types" scope. Doh! - will accept when so allows.
My problem now is trying to send the ID (editable: false) of a row when editing that row.
For example, i have a grid with columns userid(editable: false), username(editable: true), firstname(editable: true), lastname(editable: true). When editing the row the grid is only sending the parameters username, firstname and lastname. In the server side i need the userid to know to which user i've tu apply those new values.
the editUrl looks like:
editurl : CONTEXT_PATH+'/ajax/admin/savePart.do?category=1',
Thanks
This is the full code:
$.jgrid.useJSON = true;
//http://www.trirand.com/jqgridwiki/doku.php?id=wiki%3Acommon_rules
$(document).ready(function() {
//alert(CONTEXT_PATH);
var lastsel;
jQuery("#rowed3").jqGrid(
{
url : CONTEXT_PATH+'/ajax/getPartesByCategory.do?catid=<s:property value="categoryId" />',
//url : '/autoWEB/text.html',
datatype: "json",
ajaxGridOptions: { contentType: "application/json" },
jsonReader : {
root: "rows",
page: "page",
total: "total",
records: "records",
repeatitems: false
},
headertitles: true,
colNames : [ 'ID', 'Pieza', 'Disponible'],
colModel : [ {
name : 'piezaId',
index : 'piezaId',
align : "right",
width : 50,
editable : false,
required : true
}, {
name : 'descripcion',
index : 'descripcion',
width : 390,
editable : true,
required : true
}, {
name : 'disponible',
index : 'disponible',
width : 80,
editable : true,
edittype : 'select',
editoptions:{value:"0:No;1:Si"},
required : true
} ],
rowNum : 20,
rowList : [ 20, 40, 60, 80 ],
pager : '#prowed3',
sortname : 'piezaId',
postData: {piezaId : lastsel},
mtype:"POST",
viewrecords : true,
sortorder : "desc",
onSelectRow : function(id) {
if (id && id !== lastsel) {
jQuery('#rowed3').jqGrid('restoreRow', lastsel);
jQuery('#rowed3').jqGrid('editRow', id, true);
lastsel = id;
}
},
editurl : CONTEXT_PATH+'/ajax/admin/savePieza.do?categoria=<s:property value="categoryId" />',
caption : "Piezas"
});
jQuery("#rowed3").jqGrid('navGrid', "#prowed3", {
edit : false,
add : false,
del : false
});
})
in your onSelectRow callback, you can modify the editUrl to be whatever you want, including passing in the ID you need.
$("#rowed3").jqGrid('setGridParam', {editurl:'whatever/url/you/need/with/the/id'});
jqGrid will add all the other nececessary params to that editurl for you.
You can use
hidden: true, editable: true, editrules: { edithidden: false }, hidedlg: true
in the definition of the piezaId (ID) column. The parameter hidedlg is currently not real needed, but can be useful if you decide the use other jqGrid features.
Passing values in the GET string worked for me.
editurl: '/ajax/update?line=1',