Access Control Group (ACG)
Access Control Group (ACG) is a permission control mechanism required when calling Luna Bus APIs, the service bus system of webOS. ACG helps protect access to sensitive data and restricted operations, thereby supporting user privacy and system security.
Luna services group APIs based on their functionality, and apps are granted access to these APIs based on the declared group names. The webOS system then verifies whether the requesting app has the appropriate permissions, improving transparency and control over potentially sensitive or risky app behaviors.
Platform support
webOS version | ACG support | Notes |
|---|---|---|
webOS TV 25 or lower | Not supported | |
webOS TV 26 Re:New | Supported | ACG enforcement is available. If the `requiredACG` field is added to appinfo.json, ACG permissions are applied and can be tested. This allows early adoption and verification before webOS TV 27 makes it mandatory. |
webOS TV 27 or higher | Required | All apps must include the `requiredACG` field in appinfo.json — even if they do not make any Luna API calls. The `requiredACG` field is a mandatory item in the Seller Lounge eligibility check, so apps without it will fail validation and cannot be submitted. |
On webOS TV 27 or higher, the `requiredACG` field is a mandatory item in the Seller Lounge eligibility check for all apps, including those that do not call any Luna APIs. If your app does not use Luna APIs, declare an empty array (`"requiredACG": []`). Apps without this field will fail the eligibility validation and cannot be submitted.
API ACG list
The table below lists the ACG group for each publicly available Luna service method. See this table to determine the ACG groups required for the methods used by your app.
| API Name | Service | Method | ACG |
|---|---|---|---|
com.palm.activitymanager | activity.operation | ||
activity.operation | |||
activity.operation | |||
activity.operation | |||
activity.operation | |||
activity.operation | |||
activity.operation | |||
com.webos.applicationManager | application.launcher | ||
application.query | |||
com.webos.audio | audio.operation | ||
audio.operation | |||
audio.operation | |||
com.webos.service.blegatt | blegatt.query | ||
blegatt.operation | |||
blegatt.operation | |||
blegatt.query | |||
blegatt.operation | |||
blegatt.operation | |||
blegatt.operation | |||
blegatt.operation | |||
blegatt.operation | |||
blegatt.query | |||
blegatt.operation | |||
blegatt.operation | |||
blegatt.operation | |||
blegatt.operation | |||
blegatt.operation | |||
com.palm.connectionmanager | network.query | ||
com.palm.db | database.operation | ||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
database.operation | |||
com.webos.service.sm | deviceinfo.query | ||
com.webos.service.drm | drm.operation | ||
drm.operation | |||
drm.query | |||
drm.operation | |||
drm.query | |||
com.webos.service.keymanager3 | securitykey.operation | ||
securitykey.operation | |||
securitykey.operation | |||
securitykey.operation | |||
securitykey.operation | |||
securitykey.operation | |||
securitykey.operation | |||
securitykey.operation | |||
com.webos.mediadb | mediadatabase.operation | ||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
mediadatabase.operation | |||
com.webos.service.mrcu | mrcu.query | ||
mrcu.query | |||
mrcu.operation | |||
mrcu.query | |||
mrcu.query | |||
mrcu.operation | |||
mrcu.operation | |||
mrcu.query | |||
mrcu.operation | |||
com.webos.settingsservice | settings.query | ||
com.palm.systemservice | time.query | ||
com.webos.service.tv.systemproperty | systemconfig.query |
webOSTV.js API ACG list
Some methods in the webOSTV.js library (`webOS` and `webOSDev` objects) internally call Luna Services. Even if your app does not use `webOS.service.request()` directly, calling these library methods triggers Luna API calls under the hood, so you must declare the corresponding ACG groups in the `requiredACG` field of your appinfo.json.
See the tables below to identify which methods your app uses, and declare all associated ACG groups. Methods marked with `None` do not call any Luna Service and require no ACG declaration. The webOSTV.js Version column indicates the required ACG groups per library version — as the library evolves, some methods call additional Luna APIs internally, requiring more ACG declarations
webOS API
| Method | Required ACG groups | webOSTV.js version |
|---|---|---|
systemconfig.query | v1.0.0 ~ v1.2.5 | |
systemconfig.query, settings.query, arc.query, externalinput.query | v1.2.6 ~ v1.2.12 | |
systemconfig.query, settings.query, arc.query, externalinput.query, profile.query | v1.2.13+ | |
None | v1.0.0+ | |
None | v1.0.0+ | |
None | v1.0.0+ | |
None | v1.0.0+ | |
None | v1.0.0+ | |
None | v1.0.0+ | |
Depends on the target API | v1.0.0+ |
webOSDev API
Method | Required ACG groups | webOSTV.js version |
|---|---|---|
application.launcher | v1.0.0+ | |
None | v1.0.0+ | |
deviceinfo.query | v1.0.0+ | |
network.query | v1.0.0+ | |
drm.operation | v1.0.0+ | |
None | v1.0.0+ | |
drm.operation, drm.query | v1.0.0+ | |
drm.operation, drm.query | v1.0.0+ | |
drm.query | v1.0.0+ | |
drm.operation | v1.0.0+ | |
drm.query | v1.0.0+ | |
drm.operation | v1.0.0+ | |
drm.operation | v1.0.0+ |
Implementation
Find the ACG group for your APIs
See the API ACG list table above to find the ACG group for each Luna API your app will call. For example, to query network status and store data in the database, your app uses the following APIs:
Service Method ACG com.palm.connectionmanagergetStatusnetwork.querycom.palm.dbputdatabase.operationDeclare ACG permissions in appinfo.json Add the ACG group values to the `requiredACG` array in your app's appinfo.json.
{ "id": "com.example.myapp", "version": "1.0.0", "vendor": "My Company", "type": "web", "title": "My App", "main": "index.html", "requiredACG": [ "network.query", "database.operation" ] }If your app does not call any Luna APIs, declare an empty array:
{ "id": "com.example.myapp", "version": "1.0.0", "vendor": "My Company", "type": "web", "title": "My App", "main": "index.html", "requiredACG": [] }Call Luna APIs from your app
Once the ACG permissions are declared, you can call the APIs from your app code.
Use webOS.service.request (direct Luna API call)// ACG required: network.query var request = webOS.service.request("luna://com.palm.connectionmanager", { method: "getStatus", parameters: { subscribe: false }, onSuccess: function (response) { console.log("Network status:", response.isInternetConnectionAvailable); console.log("WiFi state:", response.wifi.state); }, onFailure: function (error) { console.error("Failed to get network status:", error.errorCode, error.errorText); } });Use webOSTV.js library methods
The following examples use webOSTV.js library methods that internally call Luna APIs. The required ACG groups must be declared even though your code does not call `webOS.service.request()` directly.// ACG required: systemconfig.query, settings.query, arc.query, externalinput.query, profile.query webOS.deviceInfo(function (info) { console.log("Model:", info.modelName); console.log("SDK Version:", info.sdkVersion); console.log("UHD:", info.uhd); console.log("Dolby Atmos:", info.dolbyAtmos); });// ACG required: application.launcher webOSDev.launch({ id: webOSDev.APP.BROWSER, params: { target: 'https://www.example.com', }, onSuccess(res) { console.log('Browser launched'); }, onFailure(res) { console.error('Launch failed:', res.errorText); }, });
Apps with an in-app service
If your app includes an in-app service that calls Luna APIs, the ACG groups required by those APIs must also be declared in the app's appinfo.json. See the API ACG list table for the ACG group of each Luna API called by the service, and add them to the `requiredACG` field along with any groups needed by the app itself.
The following example shows an in-app service that calls the Device Unique ID API (`deviceid/getIDs`) to retrieve the device's LGUDID.
appinfo.json for an app with an in-app service
{
"id": "com.example.myapp",
"version": "1.0.0",
"vendor": "My Company",
"type": "web",
"title": "My App",
"main": "index.html",
"requiredACG": [
"deviceinfo.query"
]
}In-App Service Code :
// services/com.example.myapp.service/service.js
var Service = require("webos-service");
var service = new Service("com.example.myapp.service");
service.register("getDeviceId", function (message) {
// ACG required: deviceinfo.query (declared in app's appinfo.json)
service.call("luna://com.webos.service.sm/deviceid/getIDs", {
idType: ["LGUDID"]
}, function (response) {
if (response.payload.returnValue) {
var idList = response.payload.idList;
message.respond({
returnValue: true,
idList: idList
});
} else {
message.respond({
returnValue: false,
errorCode: response.payload.errorCode,
errorText: response.payload.errorText
});
}
});
});Verification
If an ACG group is not declared, the API call will return an error like the following:
{
"errorCode": -1,
"returnValue": false,
"errorText": "Denied method call \"{method}\" for category \"/\""
}How to identify the missing ACG group
Check the error message — it includes the denied method name (`{method}`).
See the API ACG list table above to find the method.
Note the corresponding ACG column value.
Add the missing ACG group to the `requiredACG` array in your appinfo.json.
FAQ
Q: Can I add ACG groups after my app is published?
Yes. Update the `requiredACG` field in your appinfo.json and submit a new version through Seller Lounge. The updated permissions will take effect after the new version is approved.
Q: Do I need separate ACG declarations for my in-app service?
No. All ACG groups (for both the app and its in-app service) must be declared in the app's appinfo.json. The in-app service does not have its own separate ACG declaration.
Q: My app doesn't use any Luna APIs. Do I still need `requiredACG`?
On webOS TV 27 or higher, the `requiredACG` field is mandatory for all apps regardless of whether they call Luna APIs. If your app does not use any Luna APIs, declare an empty array:
{
"id": "com.example.simpleapp",
"version": "1.0.0",
"vendor": "My Company",
"type": "web",
"title": "Simple App",
"main": "index.html",
"requiredACG": []
}Q: My app worked fine on webOS TV 25 without ACG. Do I need to update it?
If you plan to support webOS TV 26 or higher, yes. While your app may still function on webOS TV 26 without ACG declarations, on webOS TV 27 or higher, the `requiredACG` field is a mandatory item in the Seller Lounge eligibility check. All apps must include this field — even with an empty array — or they will fail validation and cannot be submitted.
Q: How do I know which ACG group an API belongs to?
See the API ACG list table in this document. Each API is mapped to its corresponding ACG group.