android MVP - 如何从模型中调用网络层?

时间:2017-04-26 03:14:11

标签: android mvp

在MVP android中我相信网络层(改造,排球等)不应该是模型的一部分。但是我需要一个关于如何构建模型的坚实范例。该模型应该是网络层在api调用完成时简单创建的单例吗?

让我们看一下我的活动主持人:

    public class MainActivityPresenter implements IMainPresenterContract, Callback {

    IMainActivityViewContract view;//todo set up a weak reference to View to avoid leakage
    NewsService interactor;

    public MainActivityPresenter(IMainActivityViewContract view, NewsService interactor) {
        this.view = view;
        this.interactor = interactor;
    }


    public void loadResource() {
        interactor.loadResource();
    }


    public void onRequestComplete(final NewsEntities newsEntities) {

        view.dataSetUpdated(newsEntities.getResults());
    }

    @Override
    public void onResult(final NewsEntities newsEntities) {
        onRequestComplete(newsEntities);
    }

    public void goToDetailsActivity(Result result) {
        view.goToDetailsActivity(result);
    }
}

所以我的问题是关于我传递给构造函数的NewsService交互器参数。我假设这应该是模型数据而不是网络服务。但是它应该是什么样的呢?目前我的看起来像这样:

    public class NewsService implements INewsServiceContract {

    private Gson gson;
    private Callback mCallback;


    public NewsService() {
        configureGson();
    }

    private static String readStream(InputStream in) {
        StringBuilder sb = new StringBuilder();
        try (BufferedReader reader = new BufferedReader(new InputStreamReader(in))) {

            String nextLine;
            while ((nextLine = reader.readLine()) != null) {
                sb.append(nextLine);
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        return sb.toString();
    }

    public void setCallBack(Callback cb) {
        mCallback = cb; // or we can set up event bus
    }

    private void configureGson() {


        GsonBuilder builder = new GsonBuilder();
        builder.excludeFieldsWithoutExposeAnnotation();
        gson = builder.create();
    }

    @Override
    public void loadResource() {
//Todo could use a loader instead help with the config change or a headless fragment
        new AsyncTask<String, String, String>() {
            @Override
            protected String doInBackground(String... params) {
                String readStream = "";
                HttpURLConnection con = null;
                try {
                    URL url = new URL("https://api.myjson.com/bins/nl6jh");
                    con = (HttpURLConnection) url.openConnection();
                    readStream = readStream(con.getInputStream());
                } catch (Exception e) {
                    e.printStackTrace();
                }

                finally {
                    if(con!=null)
                    con.disconnect();
                }
                return readStream;
            }

            @Override
            protected void onPostExecute(String result) {
                super.onPostExecute(result);
                NewsService.this.onRequestComplete(result);


            }
        }.execute();
    }

    private void onRequestComplete(String data) {

        data = data.replaceAll("\"multimedia\":\"\"", "\"multimedia\":[]");
        news.hotels.com.sample.Model.NewsEntities newsEntities = gson.fromJson(data, NewsEntities.class);
        mCallback.onResult(newsEntities);
    }
}

因此您可以看到在这种情况下NewsService正在进行网络调用。我想我不应该把这个传递给演示者。但是如何构建模型呢?谁调用了NewsService?

更新:这个问题很久以前,每个人都请使用干净的架构方法,让你的演示者对网络层一无所知。

1 个答案:

答案 0 :(得分:2)

网络调用需要位于模型层中,并且应该从演示者触发。但是它的Model层决定了数据的位置以及隐藏在Presenter层中的数据。

我自己使用一个交互器类来执行模型层中的操作,并且演示者将使用此交互器来获取数据,并且交互器将从数据库或服务器获取有关该情况的数据。

在我的回购中查看此示例项目:

https://gitlab.com/amirziarati/Echarge

我用Dagger做DI可能会让你感到困惑。只看一下包装以及我如何分层之间的关注。

更新:我使用演示者来同步来自服务器和数据库的数据,这是错误的。主持人应该对这个过程一无所知。那段时间我没有意识到这个问题。