স্থিতিশীল এআইডিএল

সেভ করা পৃষ্ঠা গুছিয়ে রাখতে 'সংগ্রহ' ব্যবহার করুন আপনার পছন্দ অনুযায়ী কন্টেন্ট সেভ করুন ও সঠিক বিভাগে রাখুন।

অ্যান্ড্রয়েড 10 স্থিতিশীল অ্যান্ড্রয়েড ইন্টারফেস ডেফিনিশন ল্যাঙ্গুয়েজ (এআইডিএল) এর জন্য সমর্থন যোগ করে, এটি এআইডিএল ইন্টারফেস দ্বারা উপলব্ধ অ্যাপ্লিকেশন প্রোগ্রাম ইন্টারফেস (এপিআই)/অ্যাপ্লিকেশন বাইনারি ইন্টারফেস (এবিআই) ট্র্যাক রাখার একটি নতুন উপায়। স্থিতিশীল এআইডিএল-এর এআইডিএল থেকে নিম্নলিখিত মূল পার্থক্য রয়েছে:

  • বিল্ড সিস্টেমে ইন্টারফেসগুলিকে aidl_interfaces দিয়ে সংজ্ঞায়িত করা হয়।
  • ইন্টারফেসে শুধুমাত্র স্ট্রাকচার্ড ডেটা থাকতে পারে। পছন্দসই প্রকারের প্রতিনিধিত্বকারী পার্সেবলগুলি স্বয়ংক্রিয়ভাবে তাদের AIDL সংজ্ঞার উপর ভিত্তি করে তৈরি করা হয় এবং স্বয়ংক্রিয়ভাবে মার্শাল করা হয় এবং অমার্জিত হয়।
  • ইন্টারফেস স্থিতিশীল হিসাবে ঘোষণা করা যেতে পারে (পিছনে-সামঞ্জস্যপূর্ণ)। যখন এটি ঘটে, তাদের API ট্র্যাক করা হয় এবং AIDL ইন্টারফেসের পাশে একটি ফাইলে সংস্করণ করা হয়।

একটি এআইডিএল ইন্টারফেস সংজ্ঞায়িত করা

aidl_interface এর একটি সংজ্ঞা এই মত দেখায়:

aidl_interface {
    name: "my-aidl",
    srcs: ["srcs/aidl/**/*.aidl"],
    local_include_dir: "srcs/aidl",
    imports: ["other-aidl"],
    versions_with_info: [
        {
            version: "1",
            imports: ["ohter-aidl-V1"],
        },
        {
            version: "2",
            imports: ["other-aidl-V3"],
        }
    ],
    stability: "vintf",
    backend: {
        java: {
            enabled: true,
            platform_apis: true,
        },
        cpp: {
            enabled: true,
        },
        ndk: {
            enabled: true,
        },
        rust: {
            enabled: true,
        },
    },

}
  • name : AIDL ইন্টারফেস মডিউলের নাম যা একটি AIDL ইন্টারফেসকে স্বতন্ত্রভাবে সনাক্ত করে।
  • srcs : AIDL সোর্স ফাইলের তালিকা যা ইন্টারফেস রচনা করে। com.acme প্যাকেজে সংজ্ঞায়িত একটি AIDL প্রকার Foo এর পাথ <base_path>/com/acme/Foo.aidl এ হওয়া উচিত, যেখানে <base_path> Android.bp ডিরেক্টরির সাথে সম্পর্কিত যেকোন ডিরেক্টরি হতে পারে। উপরের উদাহরণে, <base_path> হল srcs/aidl
  • local_include_dir : যে পথ থেকে প্যাকেজের নাম শুরু হয়। এটি উপরে ব্যাখ্যা করা <base_path> এর সাথে মিলে যায়।
  • imports : aidl_interface মডিউলগুলির একটি তালিকা যা এটি ব্যবহার করে। যদি আপনার AIDL ইন্টারফেসগুলির মধ্যে একটি ইন্টারফেস ব্যবহার করে বা অন্য aidl_interface থেকে একটি পার্সেলেবল ব্যবহার করে, তার নাম এখানে রাখুন। এটি নিজেই নাম হতে পারে, সর্বশেষ সংস্করণটি উল্লেখ করার জন্য, অথবা একটি নির্দিষ্ট সংস্করণকে উল্লেখ করার জন্য সংস্করণ প্রত্যয় (যেমন -V1 ) সহ নাম। একটি সংস্করণ নির্দিষ্ট করা Android 12 থেকে সমর্থিত
  • versions : ইন্টারফেসের পূর্ববর্তী সংস্করণগুলি যা api_dir এর অধীনে হিমায়িত করা হয়েছে, Android 11 থেকে শুরু করে, versions aidl_api/ name হিমায়িত করা হয়েছে। ইন্টারফেসের কোনো হিমায়িত সংস্করণ না থাকলে, এটি নির্দিষ্ট করা উচিত নয়, এবং সামঞ্জস্য পরীক্ষা করা হবে না। এই ক্ষেত্রটি 13 এবং উচ্চতর versions_with_info সাথে প্রতিস্থাপিত হয়েছে।
  • versions_with_info : টিপলের তালিকা, যার প্রত্যেকটিতে একটি হিমায়িত সংস্করণের নাম এবং অন্যান্য aidl_interface মডিউলের সংস্করণ আমদানি সহ একটি তালিকা রয়েছে যা aidl_interface-এর এই সংস্করণটি আমদানি করেছে। একটি AIDL ইন্টারফেসের IFACE সংস্করণ V-এর সংজ্ঞা aidl_api/ IFACE / V এ অবস্থিত। এই ক্ষেত্রটি Android 13-এ চালু করা হয়েছিল এবং এটি সরাসরি Android.bp-এ সংশোধন করার কথা নয়। *-update-api বা *-freeze-api ব্যবহার করে ক্ষেত্রটি যোগ বা আপডেট করা হয়। এছাড়াও, যখন কোনো ব্যবহারকারী *-update-api বা *-freeze-api ব্যবহার করে তখন versions ক্ষেত্রগুলি স্বয়ংক্রিয়ভাবে সংস্করণ_ versions_with_info এ স্থানান্তরিত হয়।
  • stability : এই ইন্টারফেসের স্থিতিশীলতার প্রতিশ্রুতির জন্য ঐচ্ছিক পতাকা। বর্তমানে শুধুমাত্র "vintf" সমর্থন করে। যদি এটি সেট না করা থাকে, এটি এই সংকলন প্রসঙ্গের মধ্যে স্থায়িত্ব সহ একটি ইন্টারফেসের সাথে মিলে যায় (তাই এখানে লোড করা একটি ইন্টারফেস শুধুমাত্র একসাথে কম্পাইল করা জিনিসগুলির সাথে ব্যবহার করা যেতে পারে, উদাহরণস্বরূপ system.img এ)। যদি এটি "vintf" সেট করা হয়, এটি একটি স্থিতিশীলতার প্রতিশ্রুতির সাথে মিলে যায়: যতক্ষণ পর্যন্ত এটি ব্যবহার করা হয় ততক্ষণ ইন্টারফেসটিকে স্থিতিশীল রাখতে হবে।
  • gen_trace : ট্রেসিং চালু বা বন্ধ করার জন্য ঐচ্ছিক পতাকা। ডিফল্ট false .
  • host_supported : ঐচ্ছিক পতাকা যা true সেট করা হলে উত্পন্ন লাইব্রেরিগুলি হোস্ট পরিবেশে উপলব্ধ করে।
  • unstable : ঐচ্ছিক পতাকা চিহ্নিত করতে ব্যবহৃত হয় যে এই ইন্টারফেসটি স্থিতিশীল হতে হবে না। এটি true হিসাবে সেট করা হলে, বিল্ড সিস্টেম ইন্টারফেসের জন্য API ডাম্প তৈরি করে না বা এটি আপডেট করার প্রয়োজন হয় না।
  • backend.<type>.enabled : এই ফ্ল্যাগগুলি প্রতিটি ব্যাকএন্ডকে টগল করে যেগুলির জন্য AIDL কম্পাইলার কোড তৈরি করে। বর্তমানে, চারটি ব্যাকএন্ড সমর্থিত: জাভা, সি++, এনডিকে এবং রাস্ট। Java, C++, এবং NDK ব্যাকএন্ড ডিফল্টরূপে সক্রিয় থাকে। এই তিনটি ব্যাকএন্ডের যেকোন একটির প্রয়োজন না হলে, এটি স্পষ্টভাবে নিষ্ক্রিয় করা প্রয়োজন। মরিচা ডিফল্টরূপে অক্ষম করা হয়।
  • backend.<type>.apex_available : APEX নামের তালিকা যার জন্য তৈরি করা স্টাব লাইব্রেরি উপলব্ধ।
  • backend.[cpp|java].gen_log
  • backend.[cpp|java].vndk.enabled । ডিফল্ট false .
  • backend.java.platform_apis : ঐচ্ছিক পতাকা যা নিয়ন্ত্রণ করে যে জাভা স্টাব লাইব্রেরি প্ল্যাটফর্ম থেকে ব্যক্তিগত API-এর বিপরীতে তৈরি করা হয়েছে কিনা। stability "vintf" এ সেট করা হলে এটি "true" তে সেট করা উচিত।
  • backend.java.sdk_version : SDK-এর সংস্করণ উল্লেখ করার জন্য ঐচ্ছিক পতাকা যা জাভা স্টাব লাইব্রেরি তৈরি করা হয়েছে। ডিফল্ট হল "system_current"backend.java.platform_apis সত্য হলে এটি সেট করা উচিত নয়।
  • backend.java.platform_apis : ঐচ্ছিক পতাকা যা true সেট করা উচিত যখন জেনারেট করা লাইব্রেরিগুলিকে SDK-এর পরিবর্তে প্ল্যাটফর্ম API-এর বিপরীতে তৈরি করতে হবে৷

সংস্করণ এবং সক্রিয় ব্যাকএন্ডগুলির প্রতিটি সংমিশ্রণের জন্য, একটি স্টাব লাইব্রেরি তৈরি করা হয়। একটি নির্দিষ্ট ব্যাকএন্ডের জন্য স্টাব লাইব্রেরির নির্দিষ্ট সংস্করণটি কীভাবে উল্লেখ করবেন, মডিউল নামকরণের নিয়ম দেখুন।

এআইডিএল ফাইল লেখা

স্থিতিশীল AIDL-এর ইন্টারফেসগুলি প্রথাগত ইন্টারফেসের মতোই, ব্যতীত তাদের অসংগঠিত পার্সেলেবল ব্যবহার করার অনুমতি নেই (কারণ এগুলো স্থিতিশীল নয়!)। স্থিতিশীল এআইডিএল-এর প্রাথমিক পার্থক্য হল কীভাবে পার্সেলেবলকে সংজ্ঞায়িত করা হয়। পূর্বে, পার্সেবল ফরওয়ার্ড ঘোষণা করা হয়েছিল; স্থিতিশীল AIDL-এ, পার্সেলেবল ক্ষেত্র এবং ভেরিয়েবলগুলি স্পষ্টভাবে সংজ্ঞায়িত করা হয়।

// in a file like 'some/package/Thing.aidl'
package some.package;

parcelable SubThing {
    String a = "foo";
    int b;
}

boolean , char , float , double , byte , int , long , এবং String এর জন্য একটি ডিফল্ট বর্তমানে সমর্থিত (কিন্তু প্রয়োজনীয় নয়)। অ্যান্ড্রয়েড 12-এ, ব্যবহারকারী-সংজ্ঞায়িত গণনার জন্য ডিফল্টগুলিও সমর্থিত। যখন একটি ডিফল্ট নির্দিষ্ট করা হয় না, একটি 0-এর মতো বা খালি মান ব্যবহার করা হয়। কোনো শূন্য গণনাকারী না থাকলেও ডিফল্ট মান ছাড়া গণনাগুলি 0-তে শুরু করা হয়।

স্টাব লাইব্রেরি ব্যবহার করে

আপনার মডিউলে নির্ভরতা হিসাবে স্টাব লাইব্রেরিগুলি যুক্ত করার পরে, আপনি সেগুলিকে আপনার ফাইলগুলিতে অন্তর্ভুক্ত করতে পারেন। এখানে বিল্ড সিস্টেমে স্টাব লাইব্রেরির উদাহরণ রয়েছে (এছাড়াও Android.mk লিগ্যাসি মডিউল সংজ্ঞার জন্য ব্যবহার করা যেতে পারে):

cc_... {
    name: ...,
    shared_libs: ["my-module-name-cpp"],
    ...
}
# or
java_... {
    name: ...,
    // can also be shared_libs if desire is to load a library and share
    // it among multiple users or if you only need access to constants
    static_libs: ["my-module-name-java"],
    ...
}
# or
rust_... {
    name: ...,
    rust_libs: ["my-module-name-rust"],
    ...
}

C++ এর উদাহরণ:

#include "some/package/IFoo.h"
#include "some/package/Thing.h"
...
    // use just like traditional AIDL

জাভাতে উদাহরণ:

import some.package.IFoo;
import some.package.Thing;
...
    // use just like traditional AIDL

মরিচা মধ্যে উদাহরণ:

use aidl_interface_name::aidl::some::package::{IFoo, Thing};
...
    // use just like traditional AIDL

সংস্করণ ইন্টারফেস

foo নামের একটি মডিউল ঘোষণা করা বিল্ড সিস্টেমে একটি লক্ষ্য তৈরি করে যা আপনি মডিউলের API পরিচালনা করতে ব্যবহার করতে পারেন। তৈরি করা হলে, foo-freeze-api অ্যান্ড্রয়েড সংস্করণের উপর নির্ভর করে api_dir বা aidl_api/ name অধীনে একটি নতুন API সংজ্ঞা যোগ করে এবং একটি .hash ফাইল যোগ করে, উভয়ই ইন্টারফেসের নতুন হিমায়িত সংস্করণের প্রতিনিধিত্ব করে। foo-freeze-api সংস্করণের জন্য অতিরিক্ত সংস্করণ এবং imports প্রতিফলিত করতে versions_with_info বৈশিষ্ট্য আপডেট করে। মূলত, versions_with_infoimports imports ক্ষেত্র থেকে অনুলিপি করা হয়। কিন্তু সাম্প্রতিক স্থিতিশীল সংস্করণটি আমদানির জন্য সংস্করণ_ versions_with_infoimports উল্লেখ করা হয়েছে যার কোনো স্পষ্ট সংস্করণ নেই। একবার versions_with_info প্রপার্টি নির্দিষ্ট করা হলে, বিল্ড সিস্টেম হিমায়িত সংস্করণ এবং টপ অফ ট্রি (ToT) এবং সর্বশেষ হিমায়িত সংস্করণের মধ্যে সামঞ্জস্যতা পরীক্ষা চালায়।

উপরন্তু, আপনাকে ToT সংস্করণের API সংজ্ঞা পরিচালনা করতে হবে। যখনই একটি API আপডেট করা হয়, aidl_api/ name /current আপডেট করতে foo-update-api চালান যাতে ToT সংস্করণের API সংজ্ঞা রয়েছে।

একটি ইন্টারফেসের স্থিতিশীলতা বজায় রাখতে, মালিকরা নতুন যোগ করতে পারেন:

  • একটি ইন্টারফেসের শেষের পদ্ধতি (বা স্পষ্টভাবে সংজ্ঞায়িত নতুন সিরিয়াল সহ পদ্ধতি)
  • একটি পার্সেলেবলের শেষে উপাদান (প্রতিটি উপাদানের জন্য একটি ডিফল্ট যোগ করা প্রয়োজন)
  • ধ্রুবক মান
  • অ্যান্ড্রয়েড 11-এ, গণনাকারী
  • Android 12-এ, একটি ইউনিয়নের শেষ পর্যন্ত ক্ষেত্র

অন্য কোন কর্মের অনুমতি নেই, এবং অন্য কেউ একটি ইন্টারফেস পরিবর্তন করতে পারে না (অন্যথায় তারা মালিকের পরিবর্তনের সাথে সংঘর্ষের ঝুঁকি রাখে)।

সমস্ত ইন্টারফেস মুক্তির জন্য হিমায়িত করা হয়েছে তা পরীক্ষা করতে, আপনি নিম্নলিখিত পরিবেশগত ভেরিয়েবল সেট দিয়ে তৈরি করতে পারেন:

  • AIDL_FROZEN_REL=true m ... - বিল্ডের জন্য সমস্ত স্থিতিশীল AIDL ইন্টারফেস হিমায়িত করা প্রয়োজন যার কোনো owner: ক্ষেত্র নির্দিষ্ট করা আছে।
  • AIDL_FROZEN_OWNERS="aosp test" - বিল্ডের জন্য owner: ক্ষেত্র "aosp" বা "পরীক্ষা" হিসাবে নির্দিষ্ট করা হয়েছে৷

আমদানির স্থিতিশীলতা

একটি ইন্টারফেসের হিমায়িত সংস্করণগুলির জন্য আমদানির সংস্করণগুলি আপডেট করা স্থিতিশীল AIDL স্তরে পিছনের দিকে সামঞ্জস্যপূর্ণ৷ যাইহোক, এইগুলি আপডেট করার জন্য সমস্ত সার্ভার এবং ক্লায়েন্ট আপডেট করতে হবে যেগুলি ইন্টারফেসের পুরানো সংস্করণ ব্যবহার করে এবং কিছু অ্যাপ্লিকেশনগুলি বিভিন্ন ধরণের সংস্করণগুলিকে মিশ্রিত করার সময় বিভ্রান্ত হতে পারে৷ সাধারণত, শুধুমাত্র-টাইপ বা সাধারণ প্যাকেজের জন্য, এটি নিরাপদ কারণ IPC লেনদেন থেকে অজানা প্রকারগুলি পরিচালনা করার জন্য কোড ইতিমধ্যেই লিখতে হবে।

অ্যান্ড্রয়েড প্ল্যাটফর্ম কোডে android.hardware.graphics.common এই ধরনের সংস্করণ আপগ্রেডের সবচেয়ে বড় উদাহরণ।

সংস্করণ ইন্টারফেস ব্যবহার করে

ইন্টারফেস পদ্ধতি

রানটাইমে, একটি পুরানো সার্ভারে নতুন পদ্ধতি কল করার চেষ্টা করার সময়, নতুন ক্লায়েন্টরা ব্যাকএন্ডের উপর নির্ভর করে একটি ত্রুটি বা একটি ব্যতিক্রম পায়।

  • cpp ব্যাকএন্ড পায় ::android::UNKNOWN_TRANSACTION
  • ndk ব্যাকএন্ড STATUS_UNKNOWN_TRANSACTION পায়।
  • java ব্যাকএন্ড android.os.RemoteException পায় একটি বার্তা সহ যে API প্রয়োগ করা হয়নি।

এটি পরিচালনা করার কৌশলগুলির জন্য অনুসন্ধান সংস্করণ এবং ডিফল্ট ব্যবহার করা দেখুন।

পার্সেবল

যখন নতুন ক্ষেত্রগুলি পার্সেলেবলগুলিতে যোগ করা হয়, পুরানো ক্লায়েন্ট এবং সার্ভারগুলি সেগুলি ফেলে দেয়। যখন নতুন ক্লায়েন্ট এবং সার্ভারগুলি পুরানো পার্সেলেবলগুলি গ্রহণ করে, তখন নতুন ক্ষেত্রগুলির জন্য ডিফল্ট মানগুলি স্বয়ংক্রিয়ভাবে পূরণ করা হয়৷ এর মানে হল একটি পার্সেবলের সমস্ত নতুন ক্ষেত্রের জন্য ডিফল্টগুলি নির্দিষ্ট করা প্রয়োজন৷

ক্লায়েন্টদের আশা করা উচিত নয় যে সার্ভারগুলি নতুন ক্ষেত্রগুলি ব্যবহার করবে যদি না তারা জানে যে সার্ভারটি ক্ষেত্রটি সংজ্ঞায়িত সংস্করণটি বাস্তবায়ন করছে ( কোয়েরি সংস্করণগুলি দেখুন)৷

এনাম এবং ধ্রুবক

একইভাবে, ক্লায়েন্ট এবং সার্ভারদের হয় প্রত্যাখ্যান করা উচিত বা অচেনা ধ্রুবক মান এবং গণনাকারীকে যথাযথ হিসাবে উপেক্ষা করা উচিত, যেহেতু ভবিষ্যতে আরও যোগ করা হতে পারে। উদাহরণস্বরূপ, একটি সার্ভার যখন এমন একটি গণনাকারী গ্রহণ করে যা সম্পর্কে এটি জানে না তখন এটি বাতিল করা উচিত নয়। এটিকে হয় উপেক্ষা করা উচিত, অথবা কিছু ফেরত দেওয়া উচিত যাতে ক্লায়েন্ট জানে যে এটি এই বাস্তবায়নে অসমর্থিত।

ইউনিয়ন

একটি নতুন ক্ষেত্রের সাথে একটি ইউনিয়ন পাঠানোর চেষ্টা ব্যর্থ হয় যদি রিসিভার পুরানো হয় এবং ক্ষেত্র সম্পর্কে না জানে। বাস্তবায়ন নতুন ক্ষেত্রের সাথে মিলন দেখতে হবে না. ব্যর্থতা উপেক্ষা করা হয় যদি এটি একটি একমুখী লেনদেন হয়; অন্যথায় ত্রুটিটি BAD_VALUE (C++ বা NDK ব্যাকএন্ডের জন্য) বা IllegalArgumentException (জাভা ব্যাকএন্ডের জন্য)। যদি ক্লায়েন্ট একটি পুরানো সার্ভারে নতুন ফিল্ডে একটি ইউনিয়ন সেট পাঠায়, অথবা যখন এটি একটি পুরানো ক্লায়েন্ট একটি নতুন সার্ভার থেকে ইউনিয়ন গ্রহণ করে তখন ত্রুটিটি পাওয়া যায়।

মডিউল নামকরণের নিয়ম

অ্যান্ড্রয়েড 11-এ, প্রতিটি সংস্করণের সংমিশ্রণ এবং ব্যাকএন্ড সক্রিয় করার জন্য, একটি স্টাব লাইব্রেরি মডিউল স্বয়ংক্রিয়ভাবে তৈরি হয়। লিঙ্ক করার জন্য একটি নির্দিষ্ট স্টাব লাইব্রেরি মডিউল উল্লেখ করতে, aidl_interface মডিউলের নাম ব্যবহার করবেন না, তবে স্টাব লাইব্রেরি মডিউলের নাম, যা ifacename - version - backend , যেখানে

  • ifacename : aidl_interface মডিউলের নাম
  • version হয়
    • হিমায়িত সংস্করণের জন্য V version-number
    • V latest-frozen-version-number + 1 টিপ-অফ-ট্রির (এখনও হিমায়িত হওয়া) সংস্করণের জন্য
  • backend হয়
    • java ব্যাকএন্ডের জন্য জাভা,
    • C++ ব্যাকএন্ডের জন্য cpp ,
    • NDK ব্যাকএন্ডের জন্য ndk বা ndk_platform । আগেরটি অ্যাপের জন্য, আর পরেরটি প্ল্যাটফর্ম ব্যবহারের জন্য,
    • rust ব্যাকএন্ড জন্য জং.

অনুমান করুন যে foo নামের একটি মডিউল রয়েছে এবং এর সর্বশেষ সংস্করণ হল 2 , এবং এটি NDK এবং C++ উভয়কেই সমর্থন করে। এই ক্ষেত্রে, AIDL এই মডিউলগুলি তৈরি করে:

  • সংস্করণ 1 এর উপর ভিত্তি করে
    • foo-V1-(java|cpp|ndk|ndk_platform|rust)
  • সংস্করণ 2 এর উপর ভিত্তি করে (সর্বশেষ স্থিতিশীল সংস্করণ)
    • foo-V2-(java|cpp|ndk|ndk_platform|rust)
  • ToT সংস্করণের উপর ভিত্তি করে
    • foo-V3-(java|cpp|ndk|ndk_platform|rust)

Android 11 এর তুলনায়,

  • foo- backend , যা সর্বশেষ স্থিতিশীল সংস্করণে উল্লেখ করা হয় foo- V2 - backend
  • foo-unstable- backend , যা ToT সংস্করণে উল্লেখ করা হয় foo- V3 - backend

আউটপুট ফাইলের নামগুলি সর্বদা মডিউল নামের মতোই হয়।

  • সংস্করণ 1: foo-V1-(cpp|ndk|ndk_platform|rust).so উপর ভিত্তি করে।
  • সংস্করণ 2 এর উপর ভিত্তি করে: foo-V2-(cpp|ndk|ndk_platform|rust).so
  • ToT সংস্করণের উপর ভিত্তি করে: foo-V3-(cpp|ndk|ndk_platform|rust).so

মনে রাখবেন যে AIDL কম্পাইলার একটি unstable সংস্করণ মডিউল তৈরি করে না বা একটি স্থিতিশীল AIDL ইন্টারফেসের জন্য একটি অ-সংস্করণ মডিউল তৈরি করে না। Android 12-এর হিসাবে, একটি স্থিতিশীল AIDL ইন্টারফেস থেকে তৈরি মডিউল নাম সর্বদা এর সংস্করণ অন্তর্ভুক্ত করে।

নতুন মেটা ইন্টারফেস পদ্ধতি

Android 10 স্থিতিশীল AIDL-এর জন্য বেশ কয়েকটি মেটা ইন্টারফেস পদ্ধতি যোগ করে।

রিমোট অবজেক্টের ইন্টারফেস সংস্করণ জিজ্ঞাসা করা হচ্ছে

ক্লায়েন্টরা রিমোট অবজেক্টটি প্রয়োগ করা ইন্টারফেসের সংস্করণ এবং হ্যাশ অনুসন্ধান করতে পারে এবং ক্লায়েন্ট ব্যবহার করা ইন্টারফেসের মানগুলির সাথে প্রত্যাবর্তিত মানগুলির তুলনা করতে পারে।

cpp ব্যাকএন্ড সহ উদাহরণ:

sp<IFoo> foo = ... // the remote object
int32_t my_ver = IFoo::VERSION;
int32_t remote_ver = foo->getInterfaceVersion();
if (remote_ver < my_ver) {
  // the remote side is using an older interface
}

std::string my_hash = IFoo::HASH;
std::string remote_hash = foo->getInterfaceHash();

ndk (এবং ndk_platform ) ব্যাকএন্ড সহ উদাহরণ:

IFoo* foo = ... // the remote object
int32_t my_ver = IFoo::version;
int32_t remote_ver = 0;
if (foo->getInterfaceVersion(&remote_ver).isOk() && remote_ver < my_ver) {
  // the remote side is using an older interface
}

std::string my_hash = IFoo::hash;
std::string remote_hash;
foo->getInterfaceHash(&remote_hash);

java ব্যাকএন্ড সহ উদাহরণ:

IFoo foo = ... // the remote object
int myVer = IFoo.VERSION;
int remoteVer = foo.getInterfaceVersion();
if (remoteVer < myVer) {
  // the remote side is using an older interface
}

String myHash = IFoo.HASH;
String remoteHash = foo.getInterfaceHash();

জাভা ভাষার জন্য, দূরবর্তী দিকটি অবশ্যই getInterfaceVersion() এবং getInterfaceHash() নিম্নরূপ প্রয়োগ করতে হবে:

class MyFoo extends IFoo.Stub {
    @Override
    public final int getInterfaceVersion() { return IFoo.VERSION; }

    @Override
    public final String getInterfaceHash() { return IFoo.HASH; }
}

এর কারণ হল জেনারেট করা ক্লাস ( IFoo , IFoo.Stub , ইত্যাদি) ক্লায়েন্ট এবং সার্ভারের মধ্যে ভাগ করা হয় (উদাহরণস্বরূপ, ক্লাসগুলি বুট ক্লাসপথে হতে পারে)। যখন ক্লাসগুলি ভাগ করা হয়, সার্ভারটি ক্লাসের নতুন সংস্করণের সাথেও লিঙ্ক করা হয় যদিও এটি ইন্টারফেসের একটি পুরানো সংস্করণ দিয়ে তৈরি করা হতে পারে। যদি এই মেটা ইন্টারফেসটি ভাগ করা ক্লাসে প্রয়োগ করা হয় তবে এটি সর্বদা নতুন সংস্করণ প্রদান করে। যাইহোক, উপরের পদ্ধতিটি প্রয়োগ করে, ইন্টারফেসের সংস্করণ নম্বরটি সার্ভারের কোডে এম্বেড করা হয়েছে (কারণ IFoo.VERSION হল একটি static final int যা রেফারেন্স করার সময় ইনলাইন করা হয়) এবং এইভাবে পদ্ধতিটি সার্ভারটি তৈরি করা সঠিক সংস্করণটি ফিরিয়ে দিতে পারে। সঙ্গে.

পুরানো ইন্টারফেসের সাথে ডিল করা

এটা সম্ভব যে একটি ক্লায়েন্ট একটি AIDL ইন্টারফেসের নতুন সংস্করণের সাথে আপডেট করা হয়েছে কিন্তু সার্ভারটি পুরানো AIDL ইন্টারফেস ব্যবহার করছে। এই ধরনের ক্ষেত্রে, একটি পুরানো ইন্টারফেসে একটি পদ্ধতি কল করা UNKNOWN_TRANSACTION

স্থিতিশীল AIDL এর সাথে, ক্লায়েন্টদের আরও নিয়ন্ত্রণ থাকে। ক্লায়েন্ট সাইডে, আপনি একটি AIDL ইন্টারফেসে একটি ডিফল্ট বাস্তবায়ন সেট করতে পারেন। ডিফল্ট বাস্তবায়নে একটি পদ্ধতি চালু করা হয় যখন পদ্ধতিটি দূরবর্তী দিকে প্রয়োগ করা হয় না (কারণ এটি ইন্টারফেসের একটি পুরানো সংস্করণ দিয়ে তৈরি করা হয়েছিল)। যেহেতু ডিফল্টগুলি বিশ্বব্যাপী সেট করা হয়েছে, সেগুলি সম্ভাব্য ভাগ করা প্রসঙ্গে ব্যবহার করা উচিত নয়৷

Android 13 এবং পরবর্তীতে C++ এর উদাহরণ:

class MyDefault : public IFooDefault {
  Status anAddedMethod(...) {
   // do something default
  }
};

// once per an interface in a process
IFoo::setDefaultImpl(::android::sp<MyDefault>::make());

foo->anAddedMethod(...); // MyDefault::anAddedMethod() will be called if the
                         // remote side is not implementing it

জাভাতে উদাহরণ:

IFoo.Stub.setDefaultImpl(new IFoo.Default() {
    @Override
    public xxx anAddedMethod(...)  throws RemoteException {
        // do something default
    }
}); // once per an interface in a process


foo.anAddedMethod(...);

আপনাকে একটি AIDL ইন্টারফেসে সমস্ত পদ্ধতির ডিফল্ট বাস্তবায়ন প্রদান করতে হবে না। যে পদ্ধতিগুলি রিমোট সাইডে প্রয়োগ করার গ্যারান্টি দেওয়া হয় (কারণ আপনি নিশ্চিত যে রিমোটটি তৈরি হয়েছিল যখন পদ্ধতিগুলি এআইডিএল ইন্টারফেস বিবরণে ছিল) ডিফল্ট impl ক্লাসে ওভাররাইড করার প্রয়োজন নেই।

বিদ্যমান এআইডিএলকে কাঠামোগত/স্থিতিশীল এআইডিএলে রূপান্তর করা হচ্ছে

আপনার যদি একটি বিদ্যমান AIDL ইন্টারফেস এবং কোড থাকে যা এটি ব্যবহার করে, ইন্টারফেসটিকে একটি স্থিতিশীল AIDL ইন্টারফেসে রূপান্তর করতে নিম্নলিখিত পদক্ষেপগুলি ব্যবহার করুন৷

  1. আপনার ইন্টারফেসের সমস্ত নির্ভরতা সনাক্ত করুন। প্রতিটি প্যাকেজের জন্য ইন্টারফেস নির্ভর করে, প্যাকেজটি স্থিতিশীল AIDL-এ সংজ্ঞায়িত কিনা তা নির্ধারণ করুন। সংজ্ঞায়িত না হলে, প্যাকেজ রূপান্তর করা আবশ্যক.

  2. আপনার ইন্টারফেসের সমস্ত পার্সেবেলগুলিকে স্থিতিশীল পার্সেলেবলগুলিতে রূপান্তর করুন (ইন্টারফেস ফাইলগুলি নিজেরাই অপরিবর্তিত থাকতে পারে)। এআইডিএল ফাইলগুলিতে সরাসরি তাদের গঠন প্রকাশ করে এটি করুন। এই নতুন ধরনের ব্যবহার করার জন্য ম্যানেজমেন্ট ক্লাস পুনরায় লিখতে হবে। আপনি একটি aidl_interface প্যাকেজ (নীচে) তৈরি করার আগে এটি করা যেতে পারে।

  3. একটি aidl_interface প্যাকেজ তৈরি করুন (উপরে বর্ণিত হিসাবে) যাতে আপনার মডিউলের নাম, এর নির্ভরতা এবং আপনার প্রয়োজনীয় অন্যান্য তথ্য রয়েছে। এটিকে স্থিতিশীল করতে (শুধু কাঠামোগত নয়), এটিকে সংস্করণ করাও প্রয়োজন। আরও তথ্যের জন্য, সংস্করণ ইন্টারফেস দেখুন।