multidimensional array in angular have issue - php

What is the issue in my code?
return array is
{"records":
[{"Status":"1",
"Date":"2017-07-14 10:46:33",
"Email":"cy#gmail.com","Company":"Inc.",
"Model":"Model 8081 A","Animation":"Walk, Turn Around","id":"1",
"Note":"This is a new request for model with animation.",
"Attachment":
"[{'url':'request/31a.jpg','name':'a.jpg'},{'url':'request/42Light.png','name':'Light.png'}]"
}]
}
And HTML code is
<tr ng-repeat="x in records">
<td>{{x.Status}}</td>
<td>{{x.Date}}</td>
<td>{{x.Email}}</td>
<td>{{x.Company}}</td>
<td>{{x.Model}}</td>
<td>{{x.Animation}}</td>
<td>{{x.Note}}</td>
<td>
<table>
<tr ng-repeat="lnk in x.Attachment">
<td>{{lnk.url}}</td>
<td>{{lnk.name}}</td>
</tr>
</table>
</td>
</tr>
lnk.url and lnk.name print nothing.
Error in console is [ngRepeat:dupes]

Your attachment is not an array, it is a string. Your return array should be like this:
{
"records": [{
"Status": "1",
"Date": "2017-07-14 10:46:33",
"Email": "cy#gmail.com",
"Company": "Inc.",
"Model": "Model 8081 A",
"Animation": "Walk, Turn Around",
"id": "1",
"Note": "This is a new request for model with animation.",
"Attachment": [{
"url": "request/31a.jpg",
"name": "a.jpg"
}, {
"url": "request/42Light.png",
"name": "Light.png"
}]
}]
}
(Notice removed quotes in Attachment).
So you should convert Attachment with JSON.parse() function in your controller.

Attachment is a string not an array. convert it to an array and it will l work
angular.module("app",[])
.controller("ctrl",function($scope){
$scope.records = [
{
"Status":"1",
"Date":"2017-07-14 10:46:33",
"Email":"cy#gmail.com",
"Company":"Inc.",
"Model":"Model 8081 A",
"Animation":"Walk, Turn Around",
"id":"1",
"Note":"This is a new request for model with animation.",
"Attachment":[{'url':'request/31a.jpg','name':'a.jpg'},{'url':'request/42Light.png','name':'Light.png'}]
}
]
})
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="ctrl">
<table>
<tr ng-repeat="x in records">
<td>{{x.Status}}</td>
<td>{{x.Date}}</td>
<td>{{x.Email}}</td>
<td>{{x.Company}}</td>
<td>{{x.Model}}</td>
<td>{{x.Animation}}</td>
<td>{{x.Note}}</td>
<td>
<table>
<tr ng-repeat="lnk in x.Attachment">
<td>{{lnk.url}}</td>
<td>{{lnk.name}}</td>
</tr>
</table>
</td>
</tr>
</table>
</div>

Related

filter json data in a table when checkbox clicked

I want to filter table rows when I clicked checkbox (high, low, med, small large..)from json data according to filtered value.
I am trying here filter table rows according to filter values in the Solutions.
If I clicked High checkbox, it should show only the solution of filtered value (281) ie, SolutionID(abc1234 and abc1235).
Someone can help how to achieve the filter function for json data.
I have done this with MySql and javascript with php whereclause.
Checkboxes
<input type="checkbox" id="High" name="High" onclick="applyFilter()">
<label for="High">High</label>
<input type="checkbox" id="Medium" name="Medium" onclick="applyFilter()">
<label for="Medium">Medium</label>
<input type="checkbox" id="Low" name="Low" onclick="applyFilter()">
<label for="Low">Low</label>
json data...
Nested json data have the Filter types and values. Also has solutions I can display solutions in a table. I want to filter these solutions when I clicked checkbox, it should display only particular solutions which has filter value like 281, 283 only.
{
"Program": [
{
"Id": 2,
"Name": "Solution",
"FilterTypes": [
{
"Id": 10,
"Title": "Case",
"FilterValues": [
{
"Id": 281,
"Value": "High"
},
{
"Id": 282,
"Value": "Mid"
},
{
"Id": 283,
"Value": "Low"
}
]
},
{
"Id": 10,
"Title": "Case",
"FilterValues": [
{
"Id": 284,
"Value": "Micro"
},
{
"Id": 285,
"Value": "Small"
},
{
"Id": 286,
"Value": "Large"
}
]
}
],
"Sets": [
{
"Id": 324,
"Name": "xyz",
"Solutions": [
{
"Id": 100,
"SolutionId": "abc1234",
"Title": "XYZ Solution1",
"Published": "Tested Solution1",
"Info": "This is for perticular Solution1",
"FilterValues": [
{
"FilterValueId": 281
},
{
"FilterValueId": 283
},
{
"FilterValueId": 286
}
]
},
{
"Id": 101,
"SolutionId": "abc1235",
"Title": "XYZ Solution2",
"Published": "Tested Solution2",
"Info": "This is for perticular Solution2",
"FilterValues": [
{
"FilterValueId": 282
}
]
},
{
"Id": 102,
"SolutionId": "abc1236",
"Title": "XYZ Solution3",
"Published": "Tested Solution3",
"Info": "This is for perticular Solution3",
"FilterValues": [
{
"FilterValueId": 281
},
{
"FilterValueId": 282
}
{
"FilterValueId": 286
}
]
}
]
}
]
}
]
}
Table
Table is displaying all the solutions.
<table style="border: 5px solid; padding: 0px; width: auto;" border="1">
<thead>
<tr style="background-color: #425462; color: white">
<th style="text-align: center">Solution ID</th>
<th style="text-align: center">Published</th>
<th style="text-align: center; width:10%">Info</th>
</tr>
</thead>
<?php if(count($decoded) !=0){
foreach($decoded['Programs']['Sets']['Solutions'] as $item){
?>
<tr class="solnrow1" style="background-color:;text-align: center; width: auto">
<td style="text-align: left"><?= $item['SolutionId']?></td>
<td style="text-align: left"><?= $item['Published']?></td>
<td style="text-align: left"><?= $item['Info']?></td>
</tr>
<?php
}
}
?>

PHP Populate Table Headers Based on Data from Database

I have a table_headers database table that contains the id, header text, parent_id, and order_number that contains this data.
How do I loop to this record in such a way that it makes this kind of HTML?
<tr>
<th colspan='2'>Header 1</th>
<th colspan='6'>Header 2</th>
<th rowspan='3'>Header 3</th>
</tr>
<tr>
<th rowspan=2>H1 Child 1</th>
<th rowspan=2>H1 Child 2</th>
<th rowspan=2>h2 Child 1</th>
<th colspan=4>h2 Child 2</th>
</tr>
<tr>
<th>H2 C2 C1</th>
<th>H2 C2 C2</th>
<th>H2 C2 C3</th>
<th>H2 C2 C4</th>
</tr>
That should result to this.
Lastly, how to have an array that would contain the IDs of the lowest child just like this.
$lowest_child[0]=4; //because the ID of `H1 Child 1` is 4
$lowest_child[1]=5; //because the ID of `H1 Child 2` is 5 and so on
$lowest_child[2]=;
$lowest_child[3]=;
$lowest_child[4]=;
$lowest_child[5]=;
$lowest_child[6]=;
$lowest_child[7]=;
Another Example Data Set using the answer provided by ggordon.
It outputs to this. It seems that the order number of children is not followed.
Solution
This can be achieved after generating some helpful metadata. The code below traverses and builds a tree in an associative array. With the assistance of some helper functions getRowSpan and getColSpan the table is generated from the metadata. The json metadata generated has been included below.
In order to get the array of the lowest children. You simply need to use $levels[$depth] which will return an associative array of children at the lowest depth. The keys are the ids of the children.
HTML/PHP Code
<!DOCTYPE html>
<html>
<body>
<?php
$headings = []; # store heading data as array
$numOfRows = count($headings); # 3
$levels = [];
$depth = 0;
$subHeadings = [];
$levels[$depth]=[];
for($i=0;$i<$numOfRows;$i++){
if($headings[$i]["parent_id"]==null){
$headings[$i]["child_count"]=0;
$headings[$i]["child_ids"]=[];
$headings[$i]["depth"]=0;
$levels[$depth][$headings[$i]["id"]]=$headings[$i];
}else{
$subHeadings[]=$headings[$i];
}
}
while(count($subHeadings)>0){
$depth++;
$levels[$depth]=[];
$subHeadingNext=[];
foreach($subHeadings as $sub){
if(
isset( $levels[$depth-1][
$sub["parent_id"]
])
){
$levels[$depth-1][$sub["parent_id"]]["child_count"]++;
$levels[$depth-1][$sub["parent_id"]]["child_ids"][]=$sub["id"];
$sub["child_count"]=0;
$sub["child_ids"]=[];
$sub["depth"]=$depth;
$levels[$depth][$sub["id"]]=$sub;
}else{
$subHeadingNext[] = $sub;
}
}
$subHeadings=$subHeadingNext;
}
#echo json_encode($levels,true);
#colspan is total of all child nodes
function getColSpan($node,$levels){
$childCount = $node["child_count"];
$visitor = $node;
$childrenIds = $visitor["child_ids"];
foreach($childrenIds as $childId){
$childCount+= getColspan($levels[$visitor["depth"]+1][$childId],$levels);
}
return $childCount;
}
#max depth - depth of last child
function getRowSpan($node,$maxDepth){
return $node["child_count"] > 0 ? 1 : $maxDepth - $node["depth"]+1;
}
?>
<table border="3">
<?php
foreach($levels as $level => $nodes){
?>
<tr>
<?php
foreach($nodes as $node){
?>
<td colspan="<?php echo getColSpan($node,$levels) ?>" rowspan="<?php echo getRowSpan($node,$depth) ?>"><?php echo $node["header"] ?></td>
<?php
}
?>
</tr>
<?php
}
?>
</table>
</body>
</html>
Output
<table border="3">
<tbody><tr>
<td colspan="2" rowspan="1">Header 1</td>
<td colspan="6" rowspan="1">Header 2</td>
<td colspan="0" rowspan="3">Header 3</td>
</tr>
<tr>
<td colspan="0" rowspan="2">H1 Child 1</td>
<td colspan="0" rowspan="2">H1 Child 2</td>
<td colspan="0" rowspan="2">H2 Child 1</td>
<td colspan="4" rowspan="1">H2 Child 2</td>
</tr>
<tr>
<td colspan="0" rowspan="1">H2-C2-C1</td>
<td colspan="0" rowspan="1">H2-C2-C2</td>
<td colspan="0" rowspan="1">H2-C2-C3</td>
<td colspan="0" rowspan="1">H2-C2-C4</td>
</tr>
</tbody></table>
JSON Meta Data Generated
This is the processed result stored in $levels. It is an associated array. Each level starting from 0 can be accessed using $levels[0]. Within each level there is another associative array with nodes/tr/table cells/headings . Each heading node is indexed by the id i.e. to get Heading 1 we would use $levels[0][1]. You may see the additional metadata (depth, child ids and children count) generated and stored below:
[
{
"1":{
"id":"1",
"header":"Header 1",
"parent_id":null,
"order_number":"1",
"child_count":2,
"child_ids":[
"4",
"5"
],
"depth":0
},
"2":{
"id":"2",
"header":"Header 2",
"parent_id":null,
"order_number":"1",
"child_count":2,
"child_ids":[
"6",
"7"
],
"depth":0
},
"3":{
"id":"3",
"header":"Header 3",
"parent_id":null,
"order_number":"1",
"child_count":0,
"child_ids":[
],
"depth":0
}
},
{
"4":{
"id":"4",
"header":"H1 Child 1",
"parent_id":"1",
"order_number":"1",
"child_count":0,
"child_ids":[
],
"depth":1
},
"5":{
"id":"5",
"header":"H1 Child 2",
"parent_id":"1",
"order_number":"1",
"child_count":0,
"child_ids":[
],
"depth":1
},
"6":{
"id":"6",
"header":"H2 Child 1",
"parent_id":"2",
"order_number":"1",
"child_count":0,
"child_ids":[
],
"depth":1
},
"7":{
"id":"7",
"header":"H2 Child 2",
"parent_id":"2",
"order_number":"1",
"child_count":4,
"child_ids":[
"12",
"13",
"14",
"15"
],
"depth":1
}
},
{
"12":{
"id":"12",
"header":"H2-C2-C1",
"parent_id":"7",
"order_number":"1",
"child_count":0,
"child_ids":[
],
"depth":2
},
"13":{
"id":"13",
"header":"H2-C2-C2",
"parent_id":"7",
"order_number":"2",
"child_count":0,
"child_ids":[
],
"depth":2
},
"14":{
"id":"14",
"header":"H2-C2-C3",
"parent_id":"7",
"order_number":"3",
"child_count":0,
"child_ids":[
],
"depth":2
},
"15":{
"id":"15",
"header":"H2-C2-C4",
"parent_id":"7",
"order_number":"4",
"child_count":0,
"child_ids":[
],
"depth":2
}
}
]
Update 1: Get Nodes With No Children
The following function traverses levels to extract the nodes with no children
function getNodesWithNoChildren($levels){
$nodesWithNoChildren = [];
foreach($levels as $level => $nodes){
foreach($nodes as $node){
if($node['child_count']==0){
$nodesWithNoChildren[]=$node;
}
}
}
return $nodesWithNoChildren;
}
$nodeNamesWithNoChildren = array_map(function($node){
return $node["header"];
}, getNodesWithNoChildren($levels));
echo implode(", ",$nodeNamesWithNoChildren);
Output
Header 3, H1 Child 1, H1 Child 2, H2 Child 1, H2-C2-C1, H2-C2-C2, H2-C2-C3, H2-C2-C4
Update 2: Get Nodes With No Children (Left To Right)
function getLeftToRightNodesWithoutChildren($startNode,$levels){
$nodesWithNoChildren = [];
if($startNode == null){
foreach($levels[0] as $headerNode){
$subNodes = getLeftToRightNodesWithoutChildren($headerNode,$levels);
foreach($subNodes as $node){
$nodesWithNoChildren[]=$node;
}
}
}else{
if($startNode['child_count']==0){
$nodesWithNoChildren[]=$startNode;
}
foreach($startNode['child_ids'] as $childId){
$childNode = $levels[$startNode["depth"]+1][$childId];
$subNodes = getLeftToRightNodesWithoutChildren($childNode,$levels);
foreach($subNodes as $node){
$nodesWithNoChildren[]=$node;
}
}
}
return $nodesWithNoChildren;
}
$nodeNamesWithNoChildren = array_map(function($node){
return $node["header"];
}, getLeftToRightNodesWithoutChildren(null,$levels));
echo implode(", ",$nodeNamesWithNoChildren);
Output
H1 Child 1, H1 Child 2, H2 Child 1, H2-C2-C1, H2-C2-C2, H2-C2-C3, H2-C2-C4, Header 3
Getting "array that would contain the IDs of the lowest child"
$lowest_child = array_map(function($node){
return $node["id"];
}, getLeftToRightNodesWithoutChildren(null,$levels));
echo implode(", ",$lowest_child);
Output
4, 5, 6, 12, 13, 14, 15, 3

Record is not loading to the Datatable using php ajax

i am creating the simple crud system using php. when i load the to the datatable data is not loading.when i show the error on console Uncaught TypeError: Cannot read property 'length' of undefined
i am tring to solve out this problem since yesterday but i couldn't
Table
<table id="tbl-category" class="table table-responsive table-bordered" cellspacing="0"
width="100%">
<caption> Products</caption>
<thead>
<tr>
<th>Patient No</th>
<th>Name</th>
<th>Phone</th>
<th>Address</th>
</tr>
</table>
jQuery
function get_all() {
$('#tbl-category').dataTable().fnDestroy();
var oTable = $('#tbl-category').DataTable({
"ajax": {
"url": 'all_category.php',
"type": "get",
"datatype": "json"
},
"columns": [
{ "data": "patientno" },
{ "data": "name" },
{ "data": "phone" },
{ "data": "address" },
]
})
}
all_category.php Page
<?php
include("db.php");
$stmt = $conn->prepare("select patientno,name,phone,address from patient order by patientno DESC ");
if ($stmt->execute()) {
$stmt->bind_result($patientno,$name,$phone,$address);
while ( $stmt->fetch() ) {
$output[] = array ("patientno"=>$patientno, "name"=>$name,"phone"=>$phone,"address"=>$address);
}
echo json_encode( $output );
}
$stmt->close();

How to store the following JSON result into HTML table?

{
"total_count":3,
"offset":2,
"limit":2,
"notifications":
[
{
"id":"481a2734-6b7d-11e4-a6ea-4b53294fa671",
"successful":15,
"failed":1,
"converted":3,
"remaining":0,
"queued_at":1415914655,
"send_after":1415914655,
"canceled": false,
"url": "https://yourWebsiteToOpen.com",
"data":null,
"headings":{
"en":"English and default langauge heading",
"es":"Spanish language heading"
},
"contents":{
"en":"English and default content",
"es":"Hola"
}
},
{
"id":"b6b326a8-40aa-13e5-b91b-bf8bc3fa26f7",
"successful":5,
"failed":2,
"converted":0,
"remaining":0,
"queued_at":1415915123,
"send_after":1415915123,
"canceled": false,
"url": nil,
"data":{
"foo":"bar",
"your":"custom metadata"
},
"headings":{
"en":"English and default langauge heading",
"es":"Spanish language heading"
},
"contents":{
"en":"English and default content",
"es":"Hola"
}
}
]
}
Assuming you are wanting to display your JSON data within a HTML table, here is a basic example:
<?php
$json=<<<JSON
[
{
"name": "foo",
"age": 23,
"mood": "happy"
},
{
"name": "bar",
"age": 38,
"mood": "sad"
}
]
JSON;
$people = json_decode($json);
?>
<html>
<table>
<thead>
<tr><th>Name</th><th>Age</th><th>Mood</th></tr>
</thead>
<tbody>
<?php foreach($people as $person): ?>
<tr>
<td><?= $person->name; ?></td>
<td><?= $person->age; ?></td>
<td><?= $person->mood; ?></td>
</tr>
<?php endforeach; ?>
</tbody>
</table>
</html>
You can easily do it by using AppML, here is a tutorial which will get you started quickly.

Mandrill is not replace merge tag content in html template

Mandrill API Logs --
"subject": "Valentine’s Day special offer. Additional 10% off* on select categories! View exclusive online offer",
"from_email": "habits#zip.in",
"from_name": "zipp",
"to": [
{
"email": "xyza_123#gmail.com",
"name": "venk",
"type": "to"
}
],
"merge": true,
"merge_vars": [
{
"rcpt": "xyza_123#gmail.com",
"vars": [
{
"name": "UNSUB",
"content": "http://zyr.com/unsubscribe/GYT786HHG"
},
{
"name": "FirstName",
"content": "venk"
}
]
}
],
"async": false,
"ip_pool": null,
"send_at": null,
And when I click on the unsubscriber link in the template, it takes me to the url http://*|unsub|*. Mandrill is not replacing |UNSUB| with http://zyr.com/unsubscribe/GYT&786HHG. Please help me . I spent a lot of time on it, but am unable to solve it
<table align="left" border="0" cellpadding="0" cellspacing="0" width="100%" style="min-width:100%;" class="mcnTextContentContainer">
<tbody><tr>
<td valign="top" class="mcnTextContent" style="padding-top:9px; padding-right: 18px; padding-bottom: 9px; padding-left: 18px;">
You can unsubscribe<br>
<br>
</td>
</tr>
</tbody></table>
</td>
</tr>
</tbody>
</table>
There's no need to pass in UNSUB as a merge variable. Mandrill takes care of all of that for you. UNSUB is a reserved merge tag too, which is why it's not being replaced with the value you pass in your API call.
So in your API call, remove the merge var altogether:
{
"name": "UNSUB",
"content": "http://zyr.com/unsubscribe/GYT786HHG"
},
And in your HTML template, use this instead:
You can unsubscribe<br>

Categories