3

我需要一些关于登录过程代码基本架构的帮助。我正在实施 Async Http 处理以使事情适用于 ICS。

此代码的目标是登录我的应用程序。

  • 从 UI 提交登录表单 (Login.java)
  • 连接到我们的服务器并通过 http 传递用户名/密码获取 XML 结果
  • 将 XML 结果解析为数组。(ParseXML.java)
  • 在 UI 中显示结果反馈。

现在这一切都在我的程序中起作用了,但是在尝试使用强制 Asyc HTTP 连接的 ICS 进行测试后,我很快意识到了我的问题并让我怀疑我的整个设计......

它目前工作的基本方式:

登录.java:

  class Login {
    ...
    ParseXML myXMLParser = new ParseXML();  
    myXMLParser.doLogin(username, password, Login.this);    

    public doFinished(result) {
      // update UI
    }
    ...
  }

ParseXML.java:

  class ParseXML {
    // class variable to hold login object for async to access
    public Login loginObj;
    ...
    public void doLogin(String _username, String _password, Login _l) {
      loginObj = (Login) _l;
      ...

      // create loginUrl string to run through async
      ...
      new DownloadFilesTask().execute(loginUrl);
    }

    class DownloadFilesTask extends AsyncTask<a, b, c> {
      doInBackground() {
        // do stuff
        // download result of http call
        // parse XML
      }

      onPostExecute(result) {        
        // call the public class variable of login object i have and tell it to update the UI
        // pass back the result array.
        loginObj.doFinished(result);
      }
    }
  }

I'm mostly concerned that its bad design to be doing things this way and I should simply move the XML and http connection code within my Login.java file so its all included (UI, HTTP, XML Parsing, Asyc).

Particularly i'm concerned with calling back to Login.doFinished() from onPostExecute(). is this bad for memory? I'm worried that would cause the ParseXML object to avoid garbage collection because it is now going back to Login Activity which will continue running once the user is logged in in turn holding ParseXML open.

I come from a PHP background so I have been trying to keep all my XML parsing and HTTP processing within the ParseXML "module" so that i know where to look for changes to this.

At the moment ParseXML handles all http work, ie, getUsers, getChannels, addUser, delUser, doLogin etc. But Should I try moving all the code to handle XML and HTTP connections (async) within the relevant screen/ activity so they are self contained?

I really appreciate any help on this

4

3 回答 3

2

I would Use interface in this case

DownloadHelper.java

public interface DownloadHelper 
{
   public void OnDownloadFinish(String Response);
   public void OnDownloadFailed(String Response); 
}

Login.java

class Login {

    DownloadHelper helper=new DownloadHelper()
    {
      public void OnDownloadFinish(String Response)
       {
           // update UI

       } 

      public void OnDownloadFailed(String Response)
       {
           //Take Action
       }     
    };  


    new ParseXMLTask(this,helper).execute(username, password);
}

ParseXMLTask.java

class ParseXMLTask extends AsyncTask<Object,Object,Object>
{
    DownloadHelper helper;
    public ParseXMLTask (Context context,DownloadHelper helper)
    {
       this.helper=helper;
    }   
    public void onPreExecute(){}

    public Object DoInBackground(Object object)
    {
       // do stuff
      // download result of http call
     // parse XML
     return parsed response
    }  

   public void onPostExceute(Object object)
    {

       helper.OnDownloadFinish((String)object);
       or
        helper.OnDownloadFailed((String)object);

    }
}
于 2012-06-01T04:53:14.923 回答
1

From your post I assume that you have a LoginActivity that creates a ParseXML which then has a LoginObject (can you call that "LoginCallback"?) to return the result to the LoginActivity that displays the result. This should work, it's a callback pattern that is used a lot. A callback is generally defined as an interface, not a class.

Another approach would be to start an AsyncTask in LoginActivity, that calls ParseXML in its doInBackground, and returns the result directly to LoginActivity in onPostExecute.

于 2012-06-01T04:24:41.293 回答
1

I should simply move the XML and http connection code within my Login.java file so its all included (UI, HTTP, XML Parsing, Asyc).

This is exactly what we trying to avoid in an OO design, a big damn class contains everything (UI stuff, business logic and etc).

Based on your requirement, a good OO deisgn IMO is:

  1. Create interface IBusniessDAO define all method signatures (getUsers, getChannels and etc).
  2. Create a POJO (AKA. Plain Old Java Object) class XmlParser implements IBusinessDAO, in this class, write you method implementation normally and do not handle any asynchronous execution here (that is not the job of Business POJO). where and how these methods are intended to be used (synchronously or asynchronously) is determined in the caller class (i.e. Activity). If says in the future, you want to replace XmlParser with JsonParser, simple create JsonParser implements IBusinessDAO and replace XmlParser.
  3. AsyncTask always stay with Activity (as an inner class), if an Activity requires network functions, simply initialize you IbusinessDAO object in this Activity and call the network-related method properly in AsyncTask.doInBackground() method, and update the UI stuff managed by this activity directly in AsyncTask.onPostExecute() method.

Check out the sample code I written in this answer before, hope this helps.

于 2012-06-01T05:58:01.420 回答