Zend Framework 2的RESTful Web服务

时间:2014-06-04 23:04:48

标签: php android json rest zend-framework2

我正在开发一个代表RESTful Web服务的Zend Framework 2模块。控制器将两个参数作为输入(来自外部应用程序),使用这些参数查询指定的数据库并返回JSON。

AlbumController.php

<?php
namespace Album\Controller;


use Album\Model\Album;
use Album\Model\AlbumTable;
use Zend\Mvc\Controller\AbstractRestfulController;
use Zend\Http\Request;
use Zend\View\Model\JsonModel;
use Zend\Mvc\Controller\Plugin;

class AlbumController extends AbstractRestfulController
{

    /*public function indexAction()
    {
        return array();
    }*/

    protected $albumTable;

    public function getList()
    {

        $request = $this->getRequest();

        // if I set par1 and par statically, the service works
        $par1 = $request->getPost('par1');
        $par2 = $request->getPost('par2');

        $results = $this->getAlbumTable()->getAlbumByYearAndGenre($par1, $par2);
        $data = array();

        foreach ($results as $result) {
            $data[] = $result;
        }

        return new JsonModel(array(
            'Albums' => $data
        ));
    }

    public function getAlbumTable()
    {
        if (! $this->albumTable) {
            $sm = $this->getServiceLocator();
            $this->albumTable = $sm->get('Album\Model\AlbumTable');
        }
        return $this->albumTable;
    }

    public function get($id)
    {
        // TODO: Implement Method
    }

    public function create($data)
    {
        // TODO: Implement Method
    }

    public function update($id, $data)
    {
        // TODO: Implement Method
    }

    public function delete($id)
    {
        // TODO: Implement Method
    }
}

AlbumTable.php

<?php
namespace Album\Model;

use Zend\Db\TableGateway\TableGateway;
use Zend\ServiceManager\ServiceLocatorAwareInterface;
use Zend\ServiceManager\ServiceLocatorInterface;

class AlbumTable implements ServiceLocatorAwareInterface

{

protected $tableGateway;
protected $serviceLocator;
protected $adapter;

public function __construct(TableGateway $tableGateway)
{
    $this->tableGateway = $tableGateway;
}

public function fetchAll()
{
    $resultSet = $this->tableGateway->select();
    return $resultSet;
}

public function setServiceLocator(ServiceLocatorInterface $serviceLocator) {
    $this->serviceLocator = $serviceLocator;
}

public function getServiceLocator() {
    return $this->serviceLocator;
}

public function getAdapter()
{
    if (!$this->adapter) {
        $sl = $this->getServiceLocator();
        $this->adapter = $sl->get('db2');
    }
    return $this->adapter;
}

public function getAlbumByYearAndGenre($par1, $par2)
{




    $sql = "my query";

    $statement = $this->getAdapter()->query($sql);
    return $statement->execute();
}

}

外部应用程序(Android应用程序)使用JSONParser来检索一些信息:

public class JSONParser {

    static InputStream is = null;
    static JSONObject jObj = null;
    static String json = "";


    public JSONParser() {

    }


    public JSONObject makeHttpRequest(String url, String method,
            List<NameValuePair> params) {


        try {


            if(method == "POST"){

                DefaultHttpClient httpClient = new DefaultHttpClient();
                HttpPost httpPost = new HttpPost(url);
                httpPost.setEntity(new UrlEncodedFormEntity(params));

                HttpResponse httpResponse = httpClient.execute(httpPost);
                HttpEntity httpEntity = httpResponse.getEntity();
                is = httpEntity.getContent();
                httpClient.close();
            }else if(method == "GET"){

                DefaultHttpClient httpClient = new DefaultHttpClient();
                String paramString = URLEncodedUtils.format(params, "utf-8");
                url += "?" + paramString;
                HttpGet httpGet = new HttpGet(url);

                HttpResponse httpResponse = httpClient.execute(httpGet);
                HttpEntity httpEntity = httpResponse.getEntity();
                is = httpEntity.getContent();
                httpClient.close();
            }          

        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        } catch (ClientProtocolException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

        try {
            BufferedReader reader = new BufferedReader(new InputStreamReader(
                    is, "iso-8859-1"));
            StringBuilder sb = new StringBuilder();
            String line = null;
            while ((line = reader.readLine()) != null) {
                sb.append(line + "\n");
            }
            is.close();
            json = sb.toString();
        } catch (Exception e) {
           e.printStackTrace();
        }


        try {
            jObj = new JSONObject(json);
        } catch (JSONException e) {
            e.printStackTrace();
        }

        return jObj;

    }
}

为了模拟应用程序的行为,我创建了一个JSONParserTest:

public class JSONParserTest {
    public static void main(String[] args) {
        JSONParser jparser = new JSONParser();
        String url = "myurl";
        int par1 = 0;
        String par2 = "..."
        List<NameValuePair> params = new ArrayList<NameValuePair>();
        params.add(new BasicNameValuePair("par1", Integer.toString(par1)));
        params.add(new BasicNameValuePair("par2", par2);
        JSONObject json = jparser.makeHttpRequest(url, "POST", params);
        try {
            JSONArray jarray = json.getJSONArray("Albums");
            System.out.println(jarray.toString());
            System.out.println(json.toString());
            for(int i = 0; i < jarray.length(); i++)
            {
                JSONObject object = jarray.getJSONObject(i);
                System.out.println(object.getString("par1"));
                System.out.println(object.getString("par2"));
            } 

        } catch (JSONException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }
}

问题是如果我在控制器中静态设置参数并打开路径,我会得到JSON。但是,如果我将参数绑定到请求,似乎zend没有得到它们(我得到一个空的JSON)。事实上,这是例外:

org.json.JSONException: A JSONObject text must begin with '{' at 1 [character 2 line 1]
    at org.json.JSONTokener.syntaxError(JSONTokener.java:433)
    at org.json.JSONObject.<init>(JSONObject.java:188)
    at org.json.JSONObject.<init>(JSONObject.java:314)
    at com.example.mypackage.jclasses.JSONParser.makeHttpRequest(JSONParser.java:89)
    at com.example.mypackage.jclasses.JSONParserTest.main(JSONParserTest.java:22)
Exception in thread "main" java.lang.NullPointerException
    at com.example.mypackage.jclasses.JSONParserTest.main(JSONParserTest.java:24)

(第22行是JSONObject json = jparser.makeHttpRequest(url, "POST", params);,第24行是:JSONArray jarray = json.getJSONArray("Albums");

1 个答案:

答案 0 :(得分:0)

似乎Json字符串格式不正确。尝试做一个System.out.println(sb.toString());在你的JSONParser类中,看看StringBuilder是如何构建de Json的。

try {
  BufferedReader reader = new BufferedReader(new InputStreamReader(
    is, "iso-8859-1"));
  StringBuilder sb = new StringBuilder();
  String line = null;
  while ((line = reader.readLine()) != null) {
    sb.append(line + "\n");
  }
  is.close();
  System.out.println(sb.toString());
  json = sb.toString();
} catch (Exception e) {
   e.printStackTrace();
}