---
title:  Implementing Authorization
---

<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements.  See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License.  You may obtain a copy of the License at

     http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->

## How Authorization Works

When a component requests an operation,
the `SecurityManager.authorize` method is invoked.
It is passed the principal of the operation's requester
and a `ResourcePermission`, which describes the operation requested.

The implementation of the `SecurityManager.authorize` method
makes a decision as to whether or not the principal will be granted permission
to carry out the operation.
It returns a boolean in which a return value of `true` permits
the operation,
and a return value of `false` prevents the operation.

A well-designed `authorize` method will have or will have a way of obtaining
a mapping of principals to the operations (in the form of resource permissions)
that they are permitted to do.

## Resource Permissions

All operations are described by an instance of the `ResourcePermission` class.
A permission contains the `Resource` data member,
which classifies whether the operation as working on

- cache data; value is `DATA`
- the distributed system; value is `CLUSTER`

A permission also contains the `Operation` data member, 
which classifies whether the operation as

- reading; value is `READ`
- changing information; value is `WRITE`
- making administrative changes; value is `MANAGE`

The operations are not hierarchical;
`MANAGE` does not imply `WRITE`, and `WRITE` does not imply `READ`.

Some `DATA` operations further specify a region name in the permission.
This permits restricting operations on that region to only those
authorized principals.
And within a region, some operations may specify a key.
This permits restricting operations on that key within that region to 
only those authorized principals.

Some `CLUSTER` operations further specify a finer-grained
target for the operation.
Specify the target with a string value of:

- `DISK` to target operations that write to a disk store
- `GATEWAY` to target operations that manage gateway senders and receivers
- `QUERY` to target operations that manage both indexes and continuous
 queries
- `DEPLOY` to target operations that deploy code to servers
- `LUCENE` to target Lucene index operations

This table classifies the permissions assigned for operations common to
a Client-Server interaction.

| Client Operation                   | Assigned `ResourcePermission`
|------------------------------------|-------------------------------------|
| get function attribute             | CLUSTER:READ                        |
| create region                      | DATA:MANAGE                         |
| destroy region                     | DATA:MANAGE                         |
| Region.Keyset                      | DATA:READ:RegionName                |
| Region.query                       | DATA:READ:RegionName                |
| Region.getAll                      | DATA:READ:RegionName                |
| Region.getAll with a list of keys  | DATA:READ:RegionName:Key            |
| Region.getEntry                    | DATA:READ:RegionName                |
| Region.containsKeyOnServer(key)    | DATA:READ:RegionName:Key            |
| Region.get(key)                    | DATA:READ:RegionName:Key            |
| Region.registerInterest(key)       | DATA:READ:RegionName:Key            |
| Region.registerInterest(regex)     | DATA:READ:RegionName                |
| Region.unregisterInterest(key)     | DATA:READ:RegionName:Key            |
| Region.unregisterInterest(regex)   | DATA:READ:RegionName                |
| execute function                   | Defaults to DATA:WRITE. Override `Function.getRequiredPermissions` to change the permission. |
| clear region                       | DATA:WRITE:RegionName               |
| Region.putAll                      | DATA:WRITE:RegionName               |
| Region.clear                       | DATA:WRITE:RegionName               |
| Region.removeAll                   | DATA:WRITE:RegionName               |
| Region.destroy(key)                | DATA:WRITE:RegionName:Key           |
| Region.invalidate(key)             | DATA:WRITE:RegionName:Key           |
| Region.destroy(key)                | DATA:WRITE:RegionName:Key           |
| Region.put(key)                    | DATA:WRITE:RegionName:Key           |
| Region.replace                     | DATA:WRITE:RegionName:Key           |
| queryService.newCq                 | DATA:READ:RegionName                |
| CqQuery.stop                       | DATA:READ                           |


This table classifies the permissions assigned for `gfsh` operations.

| `gfsh` Command                         | Assigned `ResourcePermission`
|----------------------------------------|----------------------------------|
| alter disk-store                       | CLUSTER:MANAGE:DISK              |
| alter region                           | DATA:MANAGE:RegionName           |
| alter runtime                          | CLUSTER:MANAGE                   |
| backup disk-store                      | DATA:READ and CLUSTER:WRITE:DISK |
| change loglevel                        | CLUSTER:WRITE                    |
| clear defined indexes                  | CLUSTER:MANAGE:QUERY             |
| close durable-client                   | CLUSTER:MANAGE:QUERY             |
| close durable-cq                       | CLUSTER:MANAGE:QUERY             |
| compact disk-store                     | CLUSTER:MANAGE:DISK              |
| configure pdx                          | CLUSTER:MANAGE                   |
| create async-event-queue               | CLUSTER:MANAGE:DEPLOY, plus CLUSTER:WRITE:DISK if the associated region is persistent |
| create defined indexes                 | CLUSTER:MANAGE:QUERY            |
| create disk-store                      | CLUSTER:MANAGE:DISK             |
| create gateway-receiver                | CLUSTER:MANAGE:GATEWAY          |
| create gateway-sender                  | CLUSTER:MANAGE:GATEWAY          |
| create index                           | CLUSTER:MANAGE:QUERY            |
| create lucene index                    | CLUSTER:MANAGE:LUCENE            |
| create region                          | DATA:MANAGE, plus CLUSTER:WRITE:DISK if the associated region is persistent |
| define index                           | CLUSTER:MANAGE:QUERY             |
| deploy                                 | CLUSTER:MANAGE:DEPLOY            |
| describe client                        | CLUSTER:READ                     |
| describe config                        | CLUSTER:READ                     |
| describe disk-store                    | CLUSTER:READ                     |
| describe lucene index                  | CLUSTER:READ:LUCENE              |
| describe member                        | CLUSTER:READ                     |
| describe offline-disk-store            | CLUSTER:READ                     |
| describe region                        | CLUSTER:READ                     |
| destroy disk-store                     | CLUSTER:MANAGE:DISK              |
| destroy function                       | CLUSTER:MANAGE:DEPLOY            |
| destroy index                          | CLUSTER:MANAGE:QUERY             |
| destroy lucene index                   | CLUSTER:MANAGE:LUCENE            |
| destroy region                         | DATA:MANAGE                      |
| execute function                       | Defaults to DATA:WRITE. Override `Function.getRequiredPermissions` to change the permission.   |
| export cluster-configuration           | CLUSTER:READ                     |
| export config                          | CLUSTER:READ                     |
| export data                            | CLUSTER:READ                     |
| export logs                            | CLUSTER:READ                     |
| export offline-disk-store              | CLUSTER:READ                     |
| export stack-traces                    | CLUSTER:READ                     |
| gc                                     | CLUSTER:MANAGE                   |
| get &#8209;key=key1 &#8209;region=region1        | DATA:READ:RegionName:Key         |
| import data                            | DATA:WRITE:RegionName            |
| import cluster-configuration           | CLUSTER:MANAGE                   |
| list async-event-queues                | CLUSTER:READ                     |
| list clients                           | CLUSTER:READ                     |
| list deployed                          | CLUSTER:READ                     |
| list disk-stores                       | CLUSTER:READ                     |
| list durable-cqs                       | CLUSTER:READ                     |
| list functions                         | CLUSTER:READ                     |
| list gateways                          | CLUSTER:READ                     |
| list indexes                           | CLUSTER:READ:QUERY               |
| list lucene indexes                    | CLUSTER:READ:LUCENE              |
| list members                           | CLUSTER:READ                     |
| list regions                           | CLUSTER:READ                     |
| load-balance gateway-sender            | CLUSTER:MANAGE:GATEWAY           |
| locate entry                           | DATA:READ:RegionName:Key         |
| netstat                                | CLUSTER:READ                     |
| pause gateway-sender                   | CLUSTER:MANAGE:GATEWAY           |
| put --key=key1 --region=region1        | DATA:WRITE:RegionName:Key        |
| query                                  | DATA:READ:RegionName             |
| rebalance                              | DATA:MANAGE                      |
| remove                                 | DATA:WRITE:RegionName or DATA:WRITE:RegionName:Key |
| resume gateway-sender                  | CLUSTER:MANAGE:GATEWAY           |
| revoke mising-disk-store               | CLUSTER:MANAGE:DISK              |
| search lucene                          | DATA:READ:RegionName             |
| show dead-locks                        | CLUSTER:READ                     |
| show log                               | CLUSTER:READ                     |
| show metrics                           | CLUSTER:READ                     |
| show missing-disk-stores               | CLUSTER:READ                     |
| show subscription-queue-size           | CLUSTER:READ                     |
| shutdown                               | CLUSTER:MANAGE                   |
| start gateway-receiver                 | CLUSTER:MANAGE:GATEWAY           |
| start gateway-sender                   | CLUSTER:MANAGE:GATEWAY           |
| start server                           | CLUSTER:MANAGE                   |
| status cluster-config-service          | CLUSTER:READ                     |
| status gateway-receiver                | CLUSTER:READ                     |
| status gateway-sender                  | CLUSTER:READ                     |
| status locator                         | CLUSTER:READ                     |
| status server                          | CLUSTER:READ                     |
| stop gateway-receiver                  | CLUSTER:MANAGE:GATEWAY           |
| stop gateway-receiver                  | CLUSTER:MANAGE:GATEWAY           |
| stop locator                           | CLUSTER:MANAGE                   |
| stop server                            | CLUSTER:MANAGE                   |
| undeploy                               | CLUSTER:MANAGE:DEPLOY            |

The `gfsh connect` does not have a permission,
as it is the operation that invokes authentication. 
These `gfsh` commands do not have permission defined,
as they do not interact with the distributed system:

-  `gfsh describe connection`, which describes the `gfsh` end of the connection
-  `gfsh debug`, which toggles the mode within `gfsh`
-  `gfsh exit`
-  `gfsh help`
-  `gfsh hint`
-  `gfsh history`
-  `gfsh run`, although individual commands within the script
will go through authorization
-  `gfsh set variable`
-  `gfsh sh`
-  `gfsh sleep`
-  `validate offline-disk-store`
-  `gfsh version`

This table classifies the permissions assigned for JMX operations.

| JMX Operation                                | Assigned `ResourcePermission`
|----------------------------------------------|-----------------------------|
| DistributedSystemMXBean.shutdownAllMembers     | CLUSTER:MANAGE            |
| ManagerMXBean.start                            | CLUSTER:MANAGE            |
| ManagerMXBean.stop                             | CLUSTER:MANAGE            |
| ManagerMXBean.createManager                    | CLUSTER:MANAGE            |
| ManagerMXBean.shutDownMember                   | CLUSTER:MANAGE            |
| Mbeans get attributes                          | CLUSTER:READ              |
| MemberMXBean.showLog                           | CLUSTER:READ              |
| DistributedSystemMXBean.changerAlertLevel      | CLUSTER:WRITE             |
| ManagerMXBean.setPulseURL                      | CLUSTER:WRITE             |
| ManagerMXBean.setStatusMessage                 | CLUSTER:WRITE             |
| CacheServerMXBean.closeAllContinuousQuery      | CLUSTER:MANAGE:QUERY      |
| CacheServerMXBean.closeContinuousQuery         | CLUSTER:MANAGE:QUERY      |
| CacheServerMXBean.executeContinuousQuery       | DATA:READ                 |
| CqQuery.execute                    | DATA:READ:RegionName and CLUSTER:MANAGE:QUERY  |
| CqQuery.executeWithInitialResults  | DATA:READ:RegionName and CLUSTER:MANAGE:QUERY  |
| DiskStoreMXBean.flush                          | CLUSTER:MANAGE:DISK       |
| DiskStoreMXBean.forceCompaction                | CLUSTER:MANAGE:DISK       |
| DiskStoreMXBean.forceRoll                      | CLUSTER:MANAGE:DISK       |
| DiskStoreMXBean.setDiskUsageCriticalPercentage | CLUSTER:MANAGE:DISK       |
| DiskStoreMXBean.setDiskUsageWarningPercentage  | CLUSTER:MANAGE:DISK       |
| DistributedSystemMXBean.revokeMissingDiskStores| CLUSTER:MANAGE:DISK       |
| DistributedSystemMXBean.setQueryCollectionsDepth| CLUSTER:MANAGE:QUERY     |
| DistributedSystemMXBean.setQueryResultSetLimit | CLUSTER:MANAGE:QUERY      |
| DistributedSystemMXBean.backupAllMembers       | DATA:READ and CLUSTER:WRITE:DISK |
| DistributedSystemMXBean.queryData              | DATA:READ                 |
| DistributedSystemMXBean.queryDataForCompressedResult | DATA:READ           |
| GatewayReceiverMXBean.pause                    | CLUSTER:MANAGE:GATEWAY    |
| GatewayReceiverMXBean.rebalance                | CLUSTER:MANAGE:GATEWAY    |
| GatewayReceiverMXBean.resume                   | CLUSTER:MANAGE:GATEWAY    |
| GatewayReceiverMXBean.start                    | CLUSTER:MANAGE:GATEWAY    |
| GatewayReceiverMXBean.stop                     | CLUSTER:MANAGE:GATEWAY    |
| GatewaySenderMXBean.pause                      | CLUSTER:MANAGE:GATEWAY    |
| GatewaySenderMXBean.rebalance                  | CLUSTER:MANAGE:GATEWAY    |
| GatewaySenderMXBean.resume                     | CLUSTER:MANAGE:GATEWAY    |
| GatewaySenderMXBean.start                      | CLUSTER:MANAGE:GATEWAY    |
| GatewaySenderMXBean.stop                       | CLUSTER:MANAGE:GATEWAY    |
| LockServiceMXBean.becomeLockGrantor            | CLUSTER:MANAGE            |
| MemberMXBean.compactAllDiskStores              | CLUSTER:MANAGE:DISK       |

## Implement Authorization

Complete these items to implement authorization.

- Decide upon an authorization algorithm.
The [Authorization Example](authorization_example.html)
stores a mapping of which principals (users) are permitted to do
which operations.
The algorithm bases its decision
on a look up of the permissions granted to the principal attempting
the operation.
- Define the `security-manager` property.
See [Enable Security with Property Definitions](enable_security.html)
for details about this property.
- Implement the  `authorize` method of the `SecurityManager` interface.
- Define any extra resources that the implemented authorization algorithm
needs in order to make a decision.

### <a id="AuthorizeFcnExecution" class="no-quick-link"></a>Authorization of Function Execution

By default, a function executed on servers requires that the
entity invoking the function have `DATA:WRITE` permission on the
region(s) involved.
Since the default permission may not be appropriate for all functions,
the permissions required may be altered.

To implement a different set of permissions,
override the `Function.getRequiredPermissions()` method
in the function's class.
The method should return a `Collection` of the permissions
required of the entity that invokes an execution of the function.

### <a id="AuthorizeMethodsInQueries" class="no-quick-link"></a>Authorization of Methods Invoked from Queries

Enabling the `SecurityManager` affects queries
by restricting the methods that a running query may invoke.
See [Method Invocations](../../developing/query_select/the_where_clause.html#the_where_clause__section_D2F8D17B52B04895B672E2FCD675A676) for details.
