我尝试在服务器端为前端制作一些不错的结构数据。
响应应如下所示:
[
{
"id": "57484a7e0cdb86d125ebce9c",
"wasCalled": true,
"wasGood": false,
"candidateName": "Tonia Santos",
"positions": [
{
"positionId": "48asd4asd36",
"positionName": "Pozicia1"
},
{
"positionId": "954asd5as4d",
"positionName": "Pozicia4"
}
],
"addedBy": "User1",
"registered": "2014-11-30T07:13:27 -01:00"
}
]
数据库结构:
候选人:所有信息都有职位
| id | wasCalled | wasGood | addedBy | firstName | lastName的
candidates_positions:每行是一个用户和一个位置
| id | candidateId | positionId | positionName
我如何尝试:
class getCandidates
{
public function getFromDatabase(){
try {
$con = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$con->setAttribute( PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION );
$sql = "SELECT * FROM candidates as c INNER JOIN candidates_positions as cp ON c.id=cp.candidateId;";
$stmt = $con->prepare($sql);
$stmt->execute();
return $stmt->fetchAll(PDO::FETCH_ASSOC);
}catch( PDOException $e ) {
return $e->getMessage();
}
}
public function createJson($data){
return json_encode($data);
}
}
实际创建的内容:
[{
"id": "1",
"firstName": "Tonia",
"lastName": "Santos",
"addedBy": "22",
"wasCalled": "1",
"wasGood": null,
"candidateId": "1",
"positionId": "1",
"positionName": "Pozicia4"
},
{
"id": "1",
"firstName": "Tonia",
"lastName": "Santos",
"addedBy": "22",
"wasCalled": "1",
"wasGood": null,
"candidateId": "1",
"positionId": "1",
"positionName": "Pozicia1"
}]
在没有对数据库进行多次选择和构建JSON的情况下,是否有一些很好的方法或最佳实践如何创建类似于此问题的JSON?
感谢您的任何建议
答案 0 :(得分:2)
虽然您的问题已经解决,但确实看了下面的答案,但它更简洁明了。
利用MySQL的GROUP BY
和GROUP_CONCAT
条款,随后更改您的查询,
SELECT c.*, GROUP_CONCAT(cp.positionId, '|', cp.positionName) as positions
FROM candidates as c
INNER JOIN candidates_positions as cp
ON c.id=cp.candidateId
GROUP BY c.id
以下是参考资料:
所以只需按以下方式更改getFromDatabase()
方法,
public function getFromDatabase(){
try {
$con = new PDO( DB_DSN, DB_USERNAME, DB_PASSWORD );
$con->setAttribute( PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION );
$sql = "SELECT c.*, GROUP_CONCAT(cp.positionId, '|', cp.positionName) as positions FROM candidates as c INNER JOIN candidates_positions as cp ON c.id=cp.candidateId GROUP BY c.id";
$stmt = $con->prepare($sql);
$stmt->execute();
$result_arr = array();
while($result = $stmt->fetch(PDO::FETCH_ASSOC)){
$tmp_arr = array('id' => $result['id'], 'wasCalled' => $result['wasCalled'], 'wasGood' => $result['wasGood'], 'addedBy' => $result['addedBy'], 'firstName' => $result['firstName'], 'lastName' => $result['lastName']);
$positions = explode(",", $result['positions']);
foreach($positions as $s){
$components = explode("|", $s);
$tmp_arr['positions'][] = array('positionId' => $components[0], 'positionName' => $components[1]);
}
$result_arr[] = $tmp_arr;
}
return $result_arr;
}catch( PDOException $e ) {
return $e->getMessage();
}
}
稍后,您可以将返回的$result_arr
数组传递给createJson()
方法并在其上应用json_encode
。
答案 1 :(得分:1)
您可以通过更改createJson方法
来解析结果并获得所需的结果 public function createJson($data){
return_array = array();
foreach($data as $val)
{
$return_array['id']= $val['id'];
$return_array['candidateName']= $val['candidateName'];
$return_array['wasCalled']= $val['wasCalled'];
$return_array['wasGood']= $val['wasGood'];
$return_array['addedBy']= $val['addedBy'];
$return_array['positions'][] = array('positionId'=> $val['positionId'],'positionName'=>$val['positionName']);
}
return json_encode($return_array);
}
答案 2 :(得分:1)
由于你为同一个人获得了多行,包含不同的位置,它可能看起来像(从我的脑袋里打字所以可能会出现一些错误,但试试看看):
function prepare_result($data) {
$result = [];
foreach ($data as $record) {
if (!isset($result[$record['candidateId']])) {
$result[$record['candidateId']] = array(
'id' => (int) $record['candidateId'],
'wasCalled' => true,
'wasGood' => false,
'candidateName' => $record['firstName'] . " " . $record['lastName'],
'addedBy' => 'no idea', // you need additional join i think, since your result returns only ID
'registered' => 'no idea either', // same as above, original query returns no date
'positions' => array(
array(
'positionId' => $record['positionId'],
'positionName' => $record['positionName']
)
)
);
} else {
$result[$record['candidateId']]['positions'][] = array(
'positionId' => $record['positionId'],
'positionName' => $record['positionName']
);
}
}
sort($result);
return json_encode($result);
}
请注意registered
和addedBy
的评论。
答案 3 :(得分:0)
你必须改变你的查询 我应该用
select ID, if (wasCalled=1,true,false) as wasCalled, if (wasGood=1,true,false) as wasGood,
concat(firstName,' ',lastName) as candidateName, positionID, positionName,addedBy
顺便说一下,这只是一个部分解决方案,你已经将这个与TheDeceptio的答案结合起来得到你的最终解决方案。 这是必要的,因为您没有候选名称字段,您必须创建。 此外,请注意您的addedBy返回一个ID,并且您希望该名称与该ID相关联,因此我推断您还有其他一些表必须提取此信息