Alterações de políticas
Altere as definições de uma política Android, crie uma política como cópia de outra ou reverta uma política para uma versão anterior. Cada alteração é revista antes de ser aplicada.
Como funciona
Cada alteração tem dois passos. Primeiro propõe-na: a API regista uma proposta e devolve a respetiva lista de alterações, com o valor atual e novo de cada definição, o impacto e a data/hora em que a proposta expira. Nada é alterado na política ainda. Em seguida, aplica a proposta através do seu proposalId, após a pessoa responsável ter revisto a lista de alterações.
Apenas a chave de API que criou uma proposta a pode ler ou aplicar. Para uma ligação OAuth, apenas a mesma ligação e o mesmo utilizador o podem fazer. Uma proposta expira 10 minutos após ser criada; o campo expiresAt indica a hora exata.
Apenas as políticas Android podem ser alteradas desta forma. As políticas geridas pelo Nomid não o podem ser. Criar uma política também exige que a empresa esteja ligada ao Android Enterprise.
Requisitos
- Uma chave de API com a permissão POLICIES_WRITE (Alterações de políticas), combinada com POLICIES_READ. Apenas um utilizador do portal com permissão para editar políticas pode criar uma chave com POLICIES_WRITE. Necessária para os quatro endpoints POST e as ferramentas de alteração de políticas do MCP.
- A definição da empresa Alterações de políticas, em Acesso do agente de IA no portal, tem de estar ativada. Está desativada por predefinição. Enquanto estiver desativada, todas as chamadas de proposta e aplicação devolvem 403. Ler definições, revisões e propostas apenas requer POLICIES_READ.
- Os clientes MCP que se ligam com Iniciar sessão com a Nomid em vez de uma chave de API necessitam do âmbito mcp:policies:write.
Endpoints
Todos os caminhos são relativos ao URL base da API e necessitam do cabeçalho X-API-Key. Os corpos dos pedidos são em formato JSON.
| Método | Endpoint | Descrição |
|---|---|---|
| GET | /policies/{policyId}/settings | As definições editáveis da política, cada uma com o respetivo valor atual, valores permitidos, grupo e se a sua alteração é de alto impacto. Também devolve a versão da política, deviceCount e se a política é editável. |
| GET | /policies/{policyId}/revisions | As revisões guardadas da política, da mais recente para a mais antiga, com indicação de quando e por quem cada uma foi guardada. limit é opcional, de 1 a 100, predefinição 20. |
| GET | /policy-proposals/{proposalId} | Uma proposta feita por esta chave, com a respetiva lista de alterações e estado: PENDING, EXECUTING, SUCCEEDED, FAILED, UNCONFIRMED ou EXPIRED. |
| POST | /policies/{policyId}/changes | Propor alterações de definições a uma política existente. Devolve 201 com a proposta. |
| POST | /policies | Propor uma nova política como cópia de uma existente, com alterações de definições opcionais. Sem alterações, duplica a política. Devolve 201 com a proposta. |
| POST | /policies/{policyId}/rollbacks | Propor o restauro da política para uma revisão anterior. Devolve 201 com a proposta. |
| POST | /policy-proposals/{proposalId}/apply | Aplicar uma proposta pendente. Devolve 200 com a proposta e o respetivo resultado: policyId, displayName, version e uma ligação para o portal. |
Corpos de pedido
Alterar definições
| Campo | Obrigatório | Descrição |
|---|---|---|
| changes | Sim | Matriz de objetos com setting (um ID de definição) e value (um dos respetivos valores permitidos). Cada definição no máximo uma vez. Os valores não diferenciam maiúsculas de minúsculas. |
Criar uma política
| Campo | Obrigatório | Descrição |
|---|---|---|
| fromPolicyId | Sim | A política a copiar, pelo respetivo ID de política (pathName). A cópia assume as respetivas aplicações, definições e restrições. |
| displayName | Sim | Nome da nova política conforme apresentado no portal, no máximo 50 carateres. |
| changes | Não | Alterações de definições a aplicar à cópia, no mesmo formato que acima. Omita para duplicar a política. Nenhum dispositivo utiliza a nova política até mover dispositivos para a mesma. |
Reverter uma política
| Campo | Obrigatório | Descrição |
|---|---|---|
| revision | Sim | O número da revisão a restaurar, a partir do endpoint de revisões. A descrição, etiquetas e grupo da política mantêm-se inalterados. O seu nome regressa ao nome da revisão se forem diferentes, e a lista de alterações apresenta-o. |
Aplicar uma proposta
| Campo | Obrigatório | Descrição |
|---|---|---|
| confirmation | Para impacto ALTO | Obrigatório quando a proposta tem requiresConfirmation definido como true: o nome da política, introduzido pela pessoa que aprova a alteração. A correspondência ignora maiúsculas/minúsculas e espaços envolventes. |
A proposta
Todos os endpoints propose e os endpoints get e apply devolvem a proposta. Os campos mais úteis:
| Campo | Descrição |
|---|---|
| proposalId | O ID a utilizar para ler ou aplicar a proposta. |
| status | PENDING até ser aplicada e EXECUTING enquanto uma aplicação estiver em curso: nenhum é final. Depois SUCCEEDED ou FAILED, UNCONFIRMED quando um erro inesperado deixou o resultado desconhecido, ou EXPIRED assim que expiresAt tiver passado. |
| impact | NORMAL ou HIGH. Consulte Impacto e confirmação. |
| requiresConfirmation | True para uma proposta de impacto HIGH: a aplicação necessita do campo confirmation. |
| fields | A lista de alterações. Cada entrada tem label (o nome da definição), value (o novo valor) e previousValue (o valor atual). |
| summary | Uma frase a descrever a alteração, incluindo quantos dispositivos utilizam a política. |
| target | A política que a proposta altera: kind, id e name. |
| expiresAt | Quando a proposta expira. Após essa altura, já não pode ser aplicada. |
| result | Apenas respostas de aplicação: a política tal como está agora, com policyId, displayName, version, uma message e portalUrl. |
Impacto e confirmação
Uma proposta tem impacto HIGH quando a política tem pelo menos um dispositivo e qualquer uma destas condições for verdadeira:
- É uma reversão.
- Altera uma definição de alto impacto: aplicações de fontes desconhecidas, Google Play Protect, reposição de fábrica, opções de programador, transferência de dados por USB ou encriptação de armazenamento.
- A política tem 50 ou mais dispositivos, independentemente da alteração.
Tudo o resto é NORMAL, incluindo qualquer nova política, uma vez que ainda nenhum dispositivo a utiliza.
As propostas estão fixadas a uma versão da política
Uma proposta regista a versão da política sobre a qual a sua lista de alterações foi criada. Se a política for guardada novamente antes de aplicar a proposta, por qualquer pessoa e a partir de qualquer lugar, a aplicação falha com 409 e o código stale_proposal, e nada é alterado. Leia a política novamente, proponha de novo e reveja a nova lista de alterações.
Exemplo: propor e aplicar
Leia primeiro as definições atuais da política, para obter os IDs das definições e os valores permitidos:
curl "https://api.nomid.tech/emm/api/v1/policies/p7k2m9qa4xz/settings" \
-H "X-API-Key: $NOMID_API_KEY" {
"policyId": "p7k2m9qa4xz",
"displayName": "Warehouse scanners",
"version": 12,
"deviceCount": 18,
"editable": true,
"settings": [
{
"id": "CAMERA",
"label": "Camera",
"group": "RESTRICTIONS",
"value": "ALLOW",
"allowedValues": ["ALLOW", "BLOCK"],
"highImpact": false
}
]
} Propor o bloqueio da câmara e da transferência de dados por USB:
curl -X POST "https://api.nomid.tech/emm/api/v1/policies/p7k2m9qa4xz/changes" \
-H "X-API-Key: $NOMID_API_KEY" \
-H "Content-Type: application/json" \
-d '{"changes": [{"setting": "CAMERA", "value": "BLOCK"}, {"setting": "USB_DATA_ACCESS", "value": "BLOCK"}]}' HTTP/1.1 201 Created
{
"capability": "update_policy_settings",
"status": "PENDING",
"title": "Edit policy settings",
"summary": "Change 2 settings of policy \"Warehouse scanners\". 18 devices apply it on their next sync. High impact: type the policy's name to confirm.",
"target": { "kind": "policy", "id": "p7k2m9qa4xz", "name": "Warehouse scanners" },
"fields": [
{ "label": "Camera", "value": "BLOCK", "previousValue": "ALLOW" },
{ "label": "USB data transfer", "value": "BLOCK", "previousValue": "ALLOW" }
],
"expiresAt": "2026-10-09T14:40:00Z",
"impact": "HIGH",
"proposalId": "prp_7GQv2LkR9sTn4WxY8bZcA1dE",
"requiresConfirmation": true
} Resposta abreviada. A transferência de dados por USB é uma definição de alto impacto e a política tem dispositivos, pelo que a proposta tem impacto HIGH e requer confirmação. Mostre a lista de alterações à pessoa responsável antes de a aplicar.
Assim que aprovarem e escreverem o nome da política, aplique a proposta com o que foi escrito:
curl -X POST "https://api.nomid.tech/emm/api/v1/policy-proposals/prp_7GQv2LkR9sTn4WxY8bZcA1dE/apply" \
-H "X-API-Key: $NOMID_API_KEY" \
-H "Content-Type: application/json" \
-d '{"confirmation": "Warehouse scanners"}' HTTP/1.1 200 OK
{
"capability": "update_policy_settings",
"status": "SUCCEEDED",
"impact": "HIGH",
"proposalId": "prp_7GQv2LkR9sTn4WxY8bZcA1dE",
"requiresConfirmation": true,
"result": {
"policyId": "p7k2m9qa4xz",
"displayName": "Warehouse scanners",
"version": 13,
"message": "Policy settings changed. Devices on the policy apply them on their next sync."
}
} Resposta abreviada. Os dispositivos na política aplicam as novas definições na sua próxima sincronização.
Quando a política foi entretanto alterada
HTTP/1.1 409 Conflict
Content-Type: application/problem+json
{
"type": "about:blank",
"title": "Conflict",
"status": 409,
"detail": "Policy \"Warehouse scanners\" was changed after this proposal was made. Nothing was applied: read it again and propose again.",
"instance": "/emm/api/v1/policy-proposals/prp_7GQv2LkR9sTn4WxY8bZcA1dE/apply",
"code": "stale_proposal",
"retryable": false
} Definições editáveis
Estes são os IDs de definição aceites em alterações, com os respetivos valores permitidos. A etiqueta é o nome que a API devolve na lista de alterações.
Ao ler definições, um valor também pode ser NOT_SET (deixado para o dispositivo ou para a predefinição da Google) ou CUSTOM (um valor definido no portal que estes valores não conseguem expressar). Nenhum pode ser enviado, mas ambos podem ser substituídos por um valor permitido.
| Definição | Etiqueta | Grupo | Valores permitidos | Alto impacto |
|---|---|---|---|---|
| PLAY_STORE_MODE | Play Store mode | APPS | BLACKLIST, WHITELIST | Não |
| DEFAULT_PERMISSION_POLICY | Default runtime permission policy | APPS | DENY, PROMPT | Não |
| APP_AUTO_UPDATE_POLICY | App auto-update policy | APPS | ALWAYS, CHOICE_TO_THE_USER, NEVER, WIFI | Não |
| UNTRUSTED_APPS_POLICY | Apps from unknown sources | SECURITY | ALLOW_INSTALL_IN_PERSONAL_PROFILE_ONLY, DISALLOW_INSTALL | Sim |
| PLAY_PROTECT | Google Play Protect app verification | SECURITY | ENABLED, USER_CHOICE | Sim |
| SCREEN_CAPTURE | Screen capture | RESTRICTIONS | ALLOW, BLOCK | Não |
| CAMERA | Camera | RESTRICTIONS | ALLOW, BLOCK | Não |
| FACTORY_RESET | Factory reset from Settings | RESTRICTIONS | ALLOW, BLOCK | Sim |
| UNINSTALL_APPS | Uninstalling apps | RESTRICTIONS | ALLOW, BLOCK | Não |
| ACCOUNT_MODIFICATION | Adding or removing accounts | RESTRICTIONS | ALLOW, BLOCK | Não |
| ADD_USER | Adding users | RESTRICTIONS | ALLOW, BLOCK | Não |
| REMOVE_USER | Removing users | RESTRICTIONS | ALLOW, BLOCK | Não |
| DEVELOPER_SETTINGS | Developer options and USB debugging | SECURITY | ALLOW, BLOCK | Sim |
| USB_DATA_ACCESS | USB data transfer | CONNECTIVITY | ALLOW, BLOCK | Sim |
| LOCATION_MODE | Location | LOCATION | DISABLED, ENFORCED, USER_CHOICE | Não |
| LOCATION_SHARING | Sharing location | LOCATION | ALLOW, BLOCK | Não |
| OUTGOING_CALLS | Outgoing calls | RESTRICTIONS | ALLOW, BLOCK | Não |
| SMS | SMS | RESTRICTIONS | ALLOW, BLOCK | Não |
| BLUETOOTH | Bluetooth | CONNECTIVITY | ALLOW, BLOCK | Não |
| DATA_ROAMING | Data roaming | CONNECTIVITY | ALLOW, BLOCK | Não |
| NETWORK_RESET | Network settings reset | CONNECTIVITY | ALLOW, BLOCK | Não |
| VPN_CONFIGURATION | Configuring VPNs | CONNECTIVITY | ALLOW, BLOCK | Não |
| CONFIGURE_WIFI | Configuring Wi-Fi networks | CONNECTIVITY | ALLOW, BLOCK | Não |
| WIFI_DIRECT | Wi-Fi Direct | CONNECTIVITY | ALLOW, BLOCK | Não |
| TETHERING | Tethering and hotspot | CONNECTIVITY | ALLOW, BLOCK | Não |
| WIFI_STATE | Wi-Fi on or off | CONNECTIVITY | DISABLED, ENABLED, USER_CHOICE | Não |
| AIRPLANE_MODE | Airplane mode | CONNECTIVITY | DISABLED, USER_CHOICE | Não |
| MINIMUM_WIFI_SECURITY | Minimum Wi-Fi security | CONNECTIVITY | OPEN_NETWORK, PERSONAL_NETWORK | Não |
| AUTO_DATE_TIME | Automatic date, time and time zone | RESTRICTIONS | ENFORCED, USER_CHOICE | Não |
| ENCRYPTION_POLICY | Storage encryption | SECURITY | ENABLED_WITHOUT_PASSWORD, ENABLED_WITH_PASSWORD, UNSPECIFIED | Sim |
| APPLICATION_REPORT_LEVEL | Installed apps reporting | REPORTING | DISABLED, INSTALLED_AND_REMOVED_APPS, INSTALLED_APPS | Não |
| REPORT_DEVICE_SETTINGS | Device settings reporting | REPORTING | DISABLED, ENABLED | Não |
| REPORT_DISPLAY_INFO | Display information reporting | REPORTING | DISABLED, ENABLED | Não |
| REPORT_HARDWARE_STATUS | Hardware status reporting | REPORTING | DISABLED, ENABLED | Não |
| REPORT_MEMORY_INFO | Memory information reporting | REPORTING | DISABLED, ENABLED | Não |
| REPORT_NETWORK_INFO | Network information reporting | REPORTING | DISABLED, ENABLED | Não |
| REPORT_POWER_EVENTS | Power events reporting | REPORTING | DISABLED, ENABLED | Não |
| REPORT_SOFTWARE_INFO | Software information reporting | REPORTING | DISABLED, ENABLED | Não |
| REPORT_SYSTEM_PROPERTIES | System properties reporting | REPORTING | DISABLED, ENABLED | Não |
Ferramentas MCP
O servidor MCP expõe as mesmas operações como ferramentas. Aceitam os mesmos argumentos que os endpoints REST, com policyId e proposalId como argumentos em vez de segmentos de caminho.
| Ferramenta | Permissão | Descrição |
|---|---|---|
| get_policy_settings | POLICIES_READ | Ler as definições editáveis de uma política com os respetivos valores atuais e permitidos. |
| list_policy_revisions | POLICIES_READ | Listar as revisões guardadas de uma política, da mais recente para a mais antiga. |
| get_policy_proposal | POLICIES_READ | Ler uma proposta feita pela mesma chave ou ligação, com o respetivo estado. |
| update_policy_settings | POLICIES_WRITE + POLICIES_READ | Propor alterações de definições a uma política existente. |
| create_policy | POLICIES_WRITE + POLICIES_READ | Propor uma nova política como cópia de uma existente, com alterações opcionais de definições. |
| rollback_policy | POLICIES_WRITE + POLICIES_READ | Propor o restauro de uma política para uma revisão anterior. |
| apply_policy_proposal | POLICIES_WRITE + POLICIES_READ | Aplicar uma proposta pendente através do respetivo proposalId, com confirmação quando for de impacto HIGH. |
Um assistente tem de mostrar a lista de alterações ao utilizador e obter a sua aprovação explícita na conversa antes de chamar apply_policy_proposal. Para uma proposta de impacto HIGH, tem de pedir ao utilizador que escreva o nome da política e transmitir exatamente o que este escreveu.
Erros
Assim que a chave de API é autenticada, os erros usam application/problem+json com dois campos adicionais: code, um identificador estável para bifurcação condicional, e retryable, que indica se o mesmo pedido pode ser enviado novamente. Uma chave em falta ou inválida recebe a resposta 401 partilhada, um pequeno objeto JSON com error, message e status. As ferramentas MCP devolvem o mesmo code e message como um erro da ferramenta.
| Estado | Código | Significado |
|---|---|---|
| 400 | invalid_arguments | O corpo é inválido: uma definição desconhecida, um valor que não é permitido, uma definição listada duas vezes ou um campo em falta. O detalhe indica qual. |
| 403 | forbidden | A chave não tem POLICIES_WRITE ou POLICIES_READ, ou a definição da empresa Policy changes está desativada. |
| 404 | not_found | Nenhuma política ou revisão visível para esta chave, ou nenhuma proposta com este ID feita por esta chave. |
| 409 | unsupported | A política não pode ser alterada desta forma: não é uma política Android ou é gerida pelo Nomid. |
| 409 | not_pending | A proposta já não está PENDING. Leia-a para ver o respetivo estado: se for SUCCEEDED, a alteração foi efetuada. Se for EXECUTING, leia-a novamente até terminar. Se for UNCONFIRMED, leia as definições da política antes de propor novamente. Se for FAILED ou EXPIRED, proponha novamente. |
| 409 | stale_proposal | A política foi guardada após a criação da proposta. Nada foi aplicado. Leia a política novamente e proponha de novo. |
| 422 | refused | O pedido não pode ser executado: nada mudaria, a empresa não está associada ao Android Enterprise ou o novo nome da política não pode ser utilizado. |
| 422 | confirmation_required | A proposta é de impacto HIGH e a confirmação está em falta ou não coincide com o nome da política. Nada foi aplicado e a proposta permanece pendente até expirar. |
| 429 | rate_limited | Demasiados pedidos de escrita para esta chave de API ou ligação. O cabeçalho Retry-After e os detalhes indicam os segundos a aguardar. retryable é true. |
| 500 | internal_error | Erro inesperado. Leia a proposta antes de tentar novamente: se o respetivo estado for FAILED, proponha novamente. Se for UNCONFIRMED, leia as definições da política para verificar se a alteração foi efetuada antes de a propor novamente. |
Limites de taxa
Cada chamada de propose e apply conta para o limite de escrita de 10 pedidos por minuto para cada chave de API ou ligação "Iniciar sessão com o Nomid", partilhado com os endpoints de comandos de dispositivos, códigos QR de aprovisionamento e as ferramentas de escrita MCP. As chamadas de leitura não contam para este limite.
Revisões e reversão
Cada alteração aplicada guarda uma nova revisão da política. Liste as revisões para ver quem alterou a política e quando, e proponha uma reversão para anular uma alteração.