admin管理员组

文章数量:1125068

I am trying to communicate 2 android apps running on a emulator(Android 11 Pixel 4a API30) via Aidl but my client app can not bind. Here are my codes:

Client MainActivity.java

package com.example.aidl_service;

import androidx.appcompat.app.AppCompatActivity;
import android.os.Bundle;
import android.os.RemoteException;
import android.util.Log;
import android.widget.Button;
import android.widget.Toast;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.content.pm.ResolveInfo;
import android.os.IBinder;

import com.example.aidl_service.IMyAidlInterface;

import java.util.List;

public class MainActivity extends AppCompatActivity {

    Context context;
    private IMyAidlInterface aidlService;

    private final String TAG = "ClientMainAct";

    // Define the ServiceConnection for connecting to the AIDL Service
    ServiceConnection serviceConnection = new ServiceConnection() {
        @Override
        public void onServiceConnected(ComponentName componentName, IBinder iBinder) {
            aidlService = IMyAidlInterface.Stub.asInterface(iBinder);
            Toast.makeText(context, "Service Connected", Toast.LENGTH_SHORT).show();
            Log.i(TAG, "Service connected.");
        }

        @Override
        public void onServiceDisconnected(ComponentName componentName) {
            aidlService = null;
            Toast.makeText(context, "Service Disconnected", Toast.LENGTH_SHORT).show();
            Log.w(TAG, "Service disconnected.");
        }
    };

    // Bind to the AIDL Service
    private void bindAIDLService() {
        try {
            Intent intent = new Intent("com.example.aidl_service");
            intent.setPackage("com.example.aidl_service"); // Explicitly set the package name
            Intent explicitIntent = convertImplicitIntentToExplicitIntent(context, intent);

            if (explicitIntent != null) {
                bindService(explicitIntent, serviceConnection, BIND_AUTO_CREATE);
                Log.i(TAG, "Attempting to bind to the service.");
            } else {
                Log.e(TAG, "Explicit Intent conversion failed. Service may not exist.");
                Toast.makeText(context, "Failed to bind service.", Toast.LENGTH_SHORT).show();
            }
        } catch (Exception e) {
            Log.e(TAG, "Error while binding service: ", e);
        }
    }

    // Convert Implicit Intent to Explicit Intent
    private Intent convertImplicitIntentToExplicitIntent(Context context, Intent implicitIntent) {
        List<ResolveInfo> resolveInfoList = context.getPackageManager().queryIntentServices(implicitIntent, 0);
        if (resolveInfoList == null || resolveInfoList.size() != 1) {
            Log.w(TAG, "Implicit Intent resolution failed or resolved to multiple services.");
            return null;
        }

        ResolveInfo serviceInfo = resolveInfoList.get(0);
        ComponentName component = new ComponentName(serviceInfo.serviceInfo.packageName, serviceInfo.serviceInfo.name);
        Intent explicitIntent = new Intent(implicitIntent);
        explicitIntent.setComponent(component);
        return explicitIntent;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        context = this;

        // Button setup and click listener
        Button button = findViewById(R.id.button2);
        button.setOnClickListener(v -> {
            if (aidlService != null) {
                try {
                    // Send a request to the AIDL service
                    String response = aidlService.concat("a", "b");

                    Toast.makeText(this, "Response: " + response, Toast.LENGTH_SHORT).show();
                    Log.i(TAG, "Response from Service: " + response);
                } catch (RemoteException e) {
                    Log.e(TAG, "Error communicating with the service", e);
                    Toast.makeText(this, "Error communicating with the service", Toast.LENGTH_SHORT).show();
                }
            } else {
                Toast.makeText(this, "Service not bound!", Toast.LENGTH_SHORT).show();
                Log.w(TAG, "Service not bound!");
            }
        });

        bindAIDLService(); // Bind to the service on app launch
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        if (serviceConnection != null) {
            unbindService(serviceConnection); // Unbind the service when the activity is destroyed
            Log.i(TAG, "Service unbound.");
        }
    }
}

Client android manifest

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android=";
    xmlns:tools=";>

    <!-- Add permission to bind to the service -->
    <uses-permission android:name="android.permission.BIND_REMOTE_SERVICE" />

    <application
        android:allowBackup="true"
        android:dataExtractionRules="@xml/data_extraction_rules"
        android:fullBackupContent="@xml/backup_rules"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/Theme.Client"
        tools:targetApi="31">

        <activity
            android:name=".MainActivity"
            android:exported="true">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>

My aidl

// IMyAidlInterface.aidl
package com.example.aidl_service;

// Declare any non-default types here with import statements

interface IMyAidlInterface {
    String concat(String s, String s1);
}

Server mAİN ACT.

package com.example.aidl_service;

import androidx.appcompat.app.AppCompatActivity;

import android.os.Bundle;
import android.content.Intent;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Intent intent = new Intent(this, MyService.class);
        startService(intent);

    }
}

Server Service

package com.example.aidl_service;

import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import android.util.Log;

public class MyService extends Service {

    private static final String TAG = "MyAidlService";

    @Override
    public void onCreate() {
        super.onCreate();
        Log.d(TAG, "Service created.");
    }

    @Override
    public IBinder onBind(Intent intent) {
        Log.d(TAG, "Service bound.");
        return binder;
    }

    @Override
    public boolean onUnbind(Intent intent) {
        Log.d(TAG, "Service unbound.");
        return super.onUnbind(intent);
    }

    private final IMyAidlInterface.Stub binder = new IMyAidlInterface.Stub() {
        @Override
        public String concat(String str1, String str2) {
            Log.d(TAG, "concat called with: " + str1 + " and " + str2);
            return str1 + str2;
        }
    };
}

Server android manifest

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android=";
    xmlns:tools=";>
    <uses-permission android:name="android.permission.BIND_REMOTE_SERVICE" />

    <application

        android:allowBackup="true"
        android:dataExtractionRules="@xml/data_extraction_rules"
        android:fullBackupContent="@xml/backup_rules"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/Theme.Server"
        tools:targetApi="31">
        <activity
            android:name=".MainActivity"
            android:exported="true">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>

            <meta-data
                android:name="android.app.lib_name"
                android:value="" />
        </activity>
        <service
            android:name=".MyService"
            android:exported="true"
            android:enabled="true"
            android:permission="android.permission.BIND_SERVICE">
            <intent-filter>
                <action android:name="com.example.aidl_service" />
            </intent-filter>
        </service>
    </application>

</manifest>

I can share my gradle build files if you like. The problem is server app starts and ı can see "Service created." log on server side but when ı open the client app it says "Failed to bind service" due to this code phrASE does not work

Intent intent = new Intent("com.example.aidl_service");
            intent.setPackage("com.example.aidl_service"); // Explicitly set the package name
            Intent explicitIntent = convertImplicitIntentToExplicitIntent(context, intent);

I am trying to communicate 2 android apps via using aidl but my client app do not recognize the server.

本文标签: androidAIDL Communication Between AppsStack Overflow