Authentication and Authorization in Apache Solr using the Solr Operator (on Kubernetes)
In this tutorial we will see how to setup authentication and authorization in Apache Solr (using the Solr Operator) on Kubernetes. If you want to know how to get started with Solr on Kubernetes, check out my earlier article for a step-by-step guide. The only thing that changes from that guide over here, is the helm install
command we use to install Solr.
The security.json file
All authentication and authorization configuration, including users and permission rules for Solr are stored in a file named security.json
. When running Solr on your local machine, updating this file in your Solr installation is all it takes to setup authentication. However, deploying on Kubernetes with the operator requires some more work.
As of writing this article, the Solr Operator only supports the Basic Authentication Scheme
. In general, you have two options for configuring authentication with the operator:
- Let the operator bootstrap the
security.json
by itself. - Or, supply your own custom
security.json
to Solr.
Let’s explore both methods.
Option 1: Bootstrap Security
The easiest way to get started with Solr security is to have the operator bootstrap a security.json
as part of the initial deployment process. To activate this feature, add the following configuration to your SolrCloud CRD definition YAML:
spec:
...
solrSecurity:
authenticationType: Basic
Or if you’re using Helm, run the install command for Solr with the following chart value, where <CLOUD>
is the name of your SolrCloud deployment:
$ helm install <CLOUD>-solr apache-solr/solr --version 0.8.0 \
--set solrOptions.security.authenticationType="Basic"
With this the Solr operator bootstraps a security.json
with three predefined users: admin
, solr
and k8s-oper
. These users will have a random password generated by the operator during bootstrapping. To get the admin
password from the bootstrap secret, run the following command:
kubectl get secret <CLOUD>-solrcloud-security-bootstrap -o jsonpath='{.data.admin}' | base64 --decode
Once security.json
is bootstrapped, the operator will not update it. You’re expected to use the admin
user to access the Solr Security API or the Solr Admin UI to make further changes. Go ahead and change your user passwords with the following command:
curl --user admin:<ADMIN-PASSWORD> http://<SOLR-URL>/solr/admin/authentication -H 'Content-type:application/json' -d '{"set-user": {"admin":"<NEW-PASSWORD>", "solr":"<NEW-PASSWORD>"}}'
The k8s-oper user
The operator makes requests to secured Solr endpoints as the k8s-oper
user. Credentials for the k8s-oper
user are stored in a separate secret of type kubernetes.io/basic-auth
with the name <CLOUD>-solrcloud-basic-auth
. This user is configured with read-only access to a minimal set of endpoints
Remember, if you change the k8s-oper
password using the Solr security API, then you must update the <CLOUD>-solrcloud-basic-auth
secret with the new password or the operator will be locked out. Also, changing the password for the k8s-oper
user in the K8s secret after bootstrapping will not update Solr! You’re responsible for changing the password in both places.
The Solr Operator team recommends configuring Solr to allow un-authenticated access over HTTP to the probe endpoints (See below security.json template, with permissions where role is “null”). However, if you want to secure the probe endpoints, please refer to this section in the Solr Operator docs.
Option 2: User-provided security.json
In this method we will define a custom security.json and provide it to the Solr Operator to bootstrap it. Go ahead and create a new security.json
file with the template I’ve provided below.
{
"authentication": {
"blockUnknown": false,
"class": "solr.BasicAuthPlugin",
"credentials": {
"admin": "<ENCRYPTED-PASSWORD>",
"solr": "<ENCRYPTED-PASSWORD>",
"k8s-oper": "<ENCRYPTED-PASSWORD>"
},
"realm": "Solr Basic Auth",
"forwardCredentials": false
},
"authorization": {
"class": "solr.RuleBasedAuthorizationPlugin",
"user-role": {
"admin": ["admin", "k8s"],
"k8s-oper": ["k8s"],
"solr": ["users", "k8s"]
},
"permissions": [
{
"name": "k8s-probe-0",
"role": null,
"collection": null,
"path": "/admin/info/health"
},
{
"name": "k8s-probe-1",
"role": null,
"collection": null,
"path": "/admin/info/system"
},
{
"name": "k8s-status",
"role": "k8s",
"collection": null,
"path": "/admin/collections"
},
{
"name": "k8s-metrics",
"role": "k8s",
"collection": null,
"path": "/admin/metrics"
},
{
"name": "k8s-zk",
"role": "k8s",
"collection": null,
"path": "/admin/zookeeper/status"
},
{
"name": "k8s-ping",
"role": "k8s",
"collection": "*",
"path": "/admin/ping"
},
{
"name": "read",
"role": ["admin", "users"]
},
{
"name": "update",
"role": ["admin"]
},
{
"name": "security-read",
"role": ["admin"]
},
{
"name": "security-edit",
"role": ["admin"]
},
{
"name": "all",
"role": ["admin"]
}
]
}
}
As you can see the passwords you provide for the users must be encrypted. Solr expects the passwords in the security.json file to be encrypted as a SHA256 (password+salt) hash. You can use this Online Solr Password Encryption Tool to easily encrypt your passwords.
I would recommend you to start with this template, and make any changes from here to match your requirements. Some things to note:
- The first 6 permission objects are necessary for the operator to function properly. DO NOT exclude them in your custom security.json.
- The reason we create a
k8s-oper
user is so that the operator has access to only a minimal set of endpoints that help the operator manage our Solr pods. - For the full list of different permissions you can configure, please refer to the Predefined Permissions section in the official Solr docs.
Once your custom security.json is ready we can load it into Kubernetes as a generic secret
, using the following command:
kubectl create secret generic <CLOUD>-solr-security-json --from-file="<PATH-TO-SECURITY-JSON>/security.json"
Next, we need to create a secret of type kubernetes.io/basic-auth
in Kubernetes to hold the k8s-oper
user password. As I mentioned before, this is the user, the operator uses to make sure your Solr pods are running correctly. Go ahead create a yaml file called <CLOUD>-solrcloud-basic-auth.yaml
and copy the following into it:
apiVersion: v1
kind: Secret
metadata:
name: <CLOUD>-solrcloud-basic-auth
type: kubernetes.io/basic-auth
stringData:
username: k8s-oper
password: <K8S-OPERATOR-PASSWORD> # This doesn't need to be encrypted
After that apply the above file in Kubernetes, using the following command:
kubectl apply -f <PATH-TO-FILE>/<CLOUD>-solrcloud-basic-auth.yaml
Finally all you need to do is point the operator to the secrets we created above, by adding the following configuration to your SolrCloud CRD definition YAML:
spec:
...
solrSecurity:
authenticationType: Basic
basicAuthSecret: <CLOUD>-solrcloud-basic-auth
bootstrapSecurityJson:
name: <CLOUD>-solr-security-json
key: security.json
Or if you’re using helm, add the following chart values in your install command:
helm install <CLOUD>-solr apache-solr/solr --version 0.8.0 \
--set solrOptions.security.authenticationType="Basic" \
--set solrOptions.security.basicAuthSecret=<CLOUD>-solrcloud-basic-auth \
--set solrOptions.security.bootstrapSecurityJson.name=<CLOUD>-solr-security-json \
--set solrOptions.security.bootstrapSecurityJson.key="security.json"
Now you should be all good to go. Go ahead and try creating a new collection as the admin user, and see if authentication is working fine.
curl --user admin:<ADMIN-PASSWORD> "http://<SOLR-URL>/solr/admin/collections?action=CREATE&name=<COLLECTION-NAME>&numShards=1&replicationFactor=1&collection.configName=_default"
Once you’ve confirmed everything is working fine, you can safely delete the <CLOUD>-solr-security-json
secret in Kubernetes. However DO NOT delete the <CLOUD>-solrcloud-basic-auth
secret, as this is required for the solr operator to monitor the Solr pods.
Some things to note:
When you create a custom security.json
ensure that the user supplied in the <CLOUD>-solrcloud-basic-auth
(k8s-oper) has read access to the following endpoints:
/admin/info/health
/admin/info/system
/admin/collections
/admin/metrics
/admin/ping (for collection="*")
/admin/zookeeper/status
If you want to make updates to your authentication and authorization configuration, you can do it with the Solr Authentication API and Authorization API. This can also be done through the “Security” tab in the Solr Admin UI.
I hope you found this tutorial helpful in giving you an idea about how to setup authentication and authorization in Apache Solr using the Solr Operator. If you have any questions, leave them below and I’ll be happy to help.
Thanks for reading!