【问题标题】:Securing Android Web Service保护 Android Web 服务
【发布时间】:2013-10-01 20:09:57
【问题描述】:

我正在开发一个 Android 应用程序,该应用程序向我用 PHP 制作的 Web 服务发出请求。我从 Android 应用程序获取数据的方式是在代码后面静态传递一个 URL。用户看不到代码中的此 URL。我的 URL 是否有可能被泄露给用户并可能让该用户侵入我的网络服务?

我在 StackOverflow 找到了一个解决方案,其中提到我应该使用字符串资源来静态保存我的 URL。但是我在这里也遇到了一个问题,说Android上的资源可以在文件管理器中打开。

如果有人可以给我一个提示:

  1. 通过 Web 服务调用 PHP 内部的函数。

    公共函数 getStudents() { //获取学生JSON的代码 }

    调用类似http://mysite.com/getStudents()的函数

  2. 在 Android 中隐藏调用 Web 服务的 URL。

【问题讨论】:

  • 在某种程度上会显示 URL,所以如果真的有那么大的问题,你应该在你的网络服务上设置一些安全性......
  • 别人怎么可能仅仅通过 URL 就“入侵”你的网络服务?
  • @Supericy 我不确定说实话,我目前认为如果您在 Web 服务中的 URL 和方法名称对某人可见,这可能是一种可能性。我可能会接受 RSenApps 的建议。
  • 您不能依赖隐藏的 URL 来确保安全。密码保护网站,使用 HMAC、OAuth 或任何其他相关的授权/身份验证设计。其他任何东西本质上都是不安全的

标签: php android json security


【解决方案1】:

ASP.NET

 public string xLxS(string TABLENAME, string COLUMNS, string WHERECRTR, string TOP, string COLUMN)
        {
            string sonuc = "";
            DT = dataclass.SELECTSQL(TABLENAME, COLUMNS,TOP, WHERECRTR, "");
            if (DT.Rows.Count == 1)
            {
                if (COLUMN != "")
                {
                    sonuc = DataTableToJsonObj(DT,TABLENAME);
                }
                else
                {
                    sonuc = DT.Rows[0][COLUMN].ToString();
                }
            }
            else if(DT.Rows.Count > 1) 
            {
                sonuc = DataTableToJsonObj(DT,TABLENAME);
            }
            return sonuc.ToString();
        }

【讨论】:

    【解决方案2】:
    public class WebServis extends AppCompatActivity {
        ProgressDialog pDialog;
        // Web Servisimizdeki Namspace alanı
        private final String _Namspace      =   "http://tempuri.org/";
        // Web Servimizdeki Method ismi
        private final String _MethodName    =   "methodname";
        // Namspace ile Method isminin birleşimi
        private final String _Action        =   "http://tempuri.org/"+_MethodName;
        // Web Servisimizin Adresi
        private final String _Url           =   "http://"ip&or&domain"/WebService/Service.asmx";
        private String _ResultValue         =   "";
        Context context;
        EditText _birinci_sayi,_ikinci_sayi;
        String a,b;
        String TAG = "Response";
        String resultString;
        Object object=null;
        //priv JSONArrayAdapter getListView;
        private  ListView lv;
        ArrayList contactList;
        Button _btn_topla;
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_web_servis);
            // Topla butonumuzu tanımlıyoruz.
            _btn_topla=(Button)findViewById(R.id.button);
            // Yukarıda tanımladığımız _btn_topla butonuna tıklama olayını tanımlıyoruz.
            lv= (ListView)findViewById(R.id.listView);
            _btn_topla.setOnClickListener(new View.OnClickListener() {
                public void onClick(View v) {
                    //Hazırladığımız AsyncTask'ımızı çalıştırıyoruz..
    
                    AsyncCallWS task = new AsyncCallWS();
                    task.execute();
                }
            });
        }
        // Arkaplanda webservis işlemlerimizi yaptığımız yer.
        // AsyncTask sınıfımızdan _WebServiceAsyncTask türetiyoruz..
        private class AsyncCallWS extends AsyncTask<Void, Void, Void> {
            @Override
            protected void onPreExecute() {
                Log.i(TAG, "onPreExecute");
            }
            @Override
            protected Void doInBackground(Void... params) {
                Log.i(TAG, "doInBackground");
                calculate();
                HashMap<String, String> contact = new HashMap<>();
                showData(resultString);
                return null;
            }
            @Override
            protected void onPostExecute(Void result) {
                super.onPostExecute(result);
                Log.i(TAG, "onPostExecute"+ resultString);
                Log.i(TAG, "Step 9");
                try {
                    ListAdapter adapter = new SimpleAdapter(
                            WebServis.this, contactList,
                            R.layout.list_order, new String[]{"name", "email",
                            "adres"}, new int[]{R.id.Name,
                            R.id.Email, R.id.Adres});
                    Log.i(TAG, "Step 10");
                    lv.setAdapter(adapter);
                    Log.i(TAG, "Step 11");
                } catch (Exception e) {
                    Toast.makeText(getApplicationContext(),"Hata" + e.toString(),Toast.LENGTH_SHORT).show();
                    e.printStackTrace();
                }
            }
        }
    
        public void calculate() {
            String SOAP_ACTION = _Action;
            String METHOD_NAME = _MethodName;
            String NAMESPACE = _Namspace;
            String URL = _Url;
            try {
                //PropertyInfo propertyInfo=new PropertyInfo();
                SoapObject Request = new SoapObject(NAMESPACE, METHOD_NAME);
                Request.addProperty("TABLENAME","USER_TBL");
                Request.addProperty("COLUMNS","USERID,NAME,PASS,EPOSTA,ADRESS");
                Request.addProperty("WHERECRTR","");
                Request.addProperty("TOP","");
                Request.addProperty("COLUMN","");
                SoapSerializationEnvelope soapEnvelope = new SoapSerializationEnvelope(SoapEnvelope.VER11);
                soapEnvelope.dotNet = true;
                //soapEnvelope.headerOut = security; // this is an Element[] created before
                soapEnvelope.setOutputSoapObject(Request);
                HttpTransportSE transport = new HttpTransportSE(URL);
                transport.debug=true;
                transport.call(SOAP_ACTION, soapEnvelope);
                SoapPrimitive response = (SoapPrimitive) soapEnvelope.getResponse();
                //resultString1 = (SoapPrimitive) soapEnvelope.getResponse();
    
                resultString =response.toString();
                Log.i(TAG, "Result Celsius: " + resultString);
            } catch (Exception ex) {
               // Log.e(TAG, "Error: " + ex.getMessage());
            }
        }
        private void showData(String json) {
            String jsonStr = json;
            Log.e(TAG, "Response from json: " + jsonStr);
            if (jsonStr != null) {
                try {
                    JSONObject jsonObj = new JSONObject(jsonStr);
                    // Getting JSON Array node
                    JSONArray contacts = jsonObj.getJSONArray("USER_TBL");
                    // looping through All Contacts
                    contactList = new ArrayList<HashMap<String, String>>();
                    for (int i = 0; i < contacts.length(); i++) {
                        JSONObject c = contacts.getJSONObject(i);
                        String id = c.getString("USERID");
                        String name = c.getString("NAME");
                        String email = c.getString("EPOSTA");
                        String address = c.getString("ADRESS");
                        String pass = c.getString("PASS");
                        HashMap<String, String> contact = new HashMap<String, String>();
                        contact.put("id", id);
                        contact.put("name", name);
                        contact.put("email", email);
                        contact.put("adres", address);
                        contact.put("pass", pass);
                        //contact.put("mobile", mobile);
                        // adding contact to contact list
                         contactList.add(contact);
                    }
                } catch (final JSONException e) {
                    Log.e(TAG, "Json parsing error: " + e.getMessage());
                    runOnUiThread(new Runnable() {
                        @Override
                        public void run() {
                            Toast.makeText(getApplicationContext(),
                                    "Json parsing error: " + e.getMessage(),
                                    Toast.LENGTH_LONG)
                                    .show();
                        }
                    });
                }
            } else {
                Log.e(TAG, "Couldn't get json from server.");
                runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        Toast.makeText(getApplicationContext(),
                                "Couldn't get json from server. Check LogCat for possible errors!",
                                Toast.LENGTH_LONG)
                                .show();
                    }
                });
            }
        }
    }
    

    【讨论】:

      【解决方案3】:

      如果我对您的理解正确,您希望用户(任何拥有该应用的用户)在您的应用中看到一些数据,但不能直接下载。这意味着同时,您希望用户可以访问数据而不能访问数据,这显然是不可能的。内容行业已经尝试过无数的 DRM 方案,但都失败了。您能做的(以及 DRM 所做的)就是让数据变得更烦人。

      用户可以通过嗅探(拦截)流量来获取 URL。为防止这种情况,您应该使用 SSL,并包括一个额外的检查来限制将允许的 SSL 证书。这将阻止用户在手机上安装自己的 CA,然后使用 MitM 工具获取 URL。

      然后,您需要隐藏 URL/密钥/任何您用来将您的应用与恶意用户区分开来的内容,并尽可能深入地使用浏览器。一定要把它隐藏在代码中,并确保使用 ProGuard 使其更难阅读。

      此外,使用自定义用户代理、自定义 HTTP 标头和其他有趣的东西,检查它在服务器端返回一般错误消息,这样攻击者就不会知道你是如何发现他没有使用你的应用程序的,然后隐藏将这些添加到您的应用程序中的代码。 (其中一些内容可以使用静态调用进行设置,因此您几乎可以将其隐藏在任何地方。)

      【讨论】:

        猜你喜欢
        • 2010-09-12
        • 1970-01-01
        • 2014-09-13
        • 2011-02-05
        • 2013-10-19
        • 2011-01-31
        相关资源
        最近更新 更多