Skip to content

Instantly share code, notes, and snippets.

@deskoh
Last active October 7, 2021 08:44
Show Gist options
  • Save deskoh/e3338a3b84daa28dc8e3640ea4f50c52 to your computer and use it in GitHub Desktop.
Save deskoh/e3338a3b84daa28dc8e3640ea4f50c52 to your computer and use it in GitHub Desktop.
Solace PubSub+
# docker-compose -f PubSubStandard_singleNode.yml up
version: '3.3'
services:
primary:
container_name: pubSubStandardSingleNode
image: solace/solace-pubsub-standard:latest
shm_size: 1g
ulimits:
core: 1
nofile:
soft: 2448
hard: 38048
deploy:
restart_policy:
condition: on-failure
max_attempts: 1
ports:
#Port Mappings: Ports are mapped straight through from host to
#container. This may result in port collisions on commonly used
#ports that will cause failure of the container to start.
#Web transport
#- '80:80'
#Web transport over TLS
#- '443:443'
#SEMP over TLS
#- '943:943'
#MQTT Default VPN
- '1883:1883'
#AMQP Default VPN over TLS
#- '5671:5671'
#AMQP Default VPN
#- '5672:5672'
#MQTT Default VPN over WebSockets
- '8000:8000'
#MQTT Default VPN over WebSockets / TLS
- '8443:8443'
#MQTT Default VPN over TLS
- '8883:8883'
#SEMP / PubSub+ Manager
- '8080:8080'
#REST Default VPN
#- '9000:9000'
#REST Default VPN over TLS
#- '9443:9443'
#SMF
#- '55555:55555'
#SMF Compressed
#- '55003:55003'
#SMF over TLS
#- '55443:55443'
environment:
- username_admin_globalaccesslevel=admin
- username_admin_password=admin
- system_scaling_maxconnectioncount=100
volumes:
- ./data/jail:/usr/sw/jail
- ./data/diags:/var/lib/solace/diags
- ./data/internalSpool:/usr/sw/internalSpool
- ./data/adb:/usr/sw/adb
- ./data/softAdb:/usr/sw/internalSpool/softAdb
- ./data/var:/usr/sw/var
! Script is created to be idempotent
enable
! Setup root CA
configure
authentication
! Note: certificate-authority replaced by client-certificate-authority in newer version
! create certificate-authority rootCA.crt
create client-certificate-authority rootCA.crt
certificate file rootCA.crt
show client-certificate-authority ca-name *
end
! Setup server cert
configure
ssl server-certificate localhost.crt
ssl cipher-suite msg-backbone name AES128-SHA
end
! Delete certs
cd /certs
delete *.crt
end
! Enable client authentication
configure
message-vpn default
! Disable anonymous connection
authentication basic auth-type internal
! Enable client certificate authentication
authentication client-certificate
no shutdown
end
! Configure default ACL
configure
acl-profile default message-vpn default
publish-topic default-action disallow
subscribe-topic default-action disallow
! Add publish topic exception
publish-topic exceptions smf list device/$client-username/>
! publish-topic exceptions mqtt list device/$client-username/#
end
! Disable unused services (SEMP required for Web UI)
configure
service amqp shutdown
service rest incoming shutdown
service rest outgoing shutdown
service web-transport shutdown
end
! Disable unused non non-secure MQTT in Message VPN
configure
message-vpn default
service mqtt plain-text shutdown
service mqtt websocket shutdown
end
! Create admin ACL
configure
create acl-profile admin message-vpn default
end
configure
acl-profile admin message-vpn default
client-connect default-action allow
publish-topic default-action allow
subscribe-topic default-action allow
end
! Create admin user (password: admin) with admin ACL
configure
create client-username admin message-vpn default
end
configure
client-username admin message-vpn default
password admin
! Client Username admin must be shutdown to change the ACL profile
shutdown
acl-profile admin
no shutdown
end

Solace PubSub+

Solace CLI

Command Reference

Running CLI in Docker container: docker exec -it pubSubStandardSingleNode /usr/sw/loads/currentload/bin/cli -A

Advanced: Running CLI Scripts

# Scripts to be in /cliscripts
# -e: Auto exit mode, -s: execute CLI script
/usr/sw/loads/currentload/bin/cli -A -es /cliscripts/setup.cli

# Config dump: show current-config all > cliscripts/setup.cli

Command Context

# User EXEC
solace> enable
# Privileged EXEC
solace> configure
# Global CONFIG
solace(configure)# end

solace> admin
# Admin EXEC Level (admin from Privileged)
solace(admin)#

Session Timeout (User EXEC)

# Configure no session timeout
session timeout 0

Client User Name / Profile (User EXEC)

solace> show client-profile default
solace> show client-username default

Copy (Privileged EXEC)

copy sftp://foo@172.19.0.3/upload/rootCA.crt /certs/rootCA.crt
copy sftp://foo@172.19.0.3/upload/localhost.crt /certs/localhost.crt

Configuring User Accounts (Global CONFIG)

# Create a new CLI user account.
create username <name> password <password> cli
# Create a new File Transfer user account.
create username <name> password <password> file-transfer

# Edit the properties for an existing File Transfer account
username <name>

# Delete user
no <name>

Configure TLS Server Certificates (Global CONFIG)

For Server TLS, the Certificate Authority (CA) on the broker need not be configured.

The server certificate file must be PEM formatted. It must consist of a private key and between one and three certificates comprising the certificate trust chain. If loading from a file, it must be located in the /certs (/usr/sw/jail/certs in docker) directory.

ssl
server-certificate localhost.crt
# Alternatively, file contents can be provided:
server-certificate localhost.crt file-contents "-----BEGIN RSA PRIVATE KEY-----\n....."
cipher-suite msg-backbone name AES128-SHA

show ssl certificate-files [filename <filename>] [detail]
show ssl server-certificate [detail]
show stats ssl

Adding Client Certificate Authority / CA (Global CONFIG)

The certificate file must be PEM formatted (have a .pem extension). If loading from a file, it must be located in the /certs directory. Note that Client CA does not have private key.

authentication
! Note: Older version of PubSub+ might be using `certificate-authority` instead of `client-client-certificate-authority`
create client-certificate-authority rootCA
! To remove: no client-certificate-authority <ca-name>
certificate file rootCA.crt
# Alternativey
certificate content "-----BEGIN CERTIFICATE-----\n....."
show certificate-authority ca-name *

Generate Server Certs for TLS

Generate Self-Signed Server Root CA

The Server Root CA has to be trusted by clients. (e.g. added to client trusted store)

# Create root key (for non password-protected key, remove the -des3 option)
openssl genrsa -des3 -out serverCA.key 2048

# Create and self sign the Root Certificate
openssl req -x509 -new -key serverCA.key -sha256 -days 1825 -out serverCA.crt

# The above is equivalent to the following (for non password-protected key):
openssl req -nodes -new -x509 -newkey rsa:2048 -keyout serverCA.key -days 1825 -out serverCA.crt

Generate Server Certificate

The Server root CA need not be configured in the broker for Server TLS.

# Create the certificate key (for non password-protected key, remove the -des3 option)
openssl genrsa -des3 -out mydomain.com.key 2048

# Generate CSR
openssl req -new -key mydomain.com.key -out mydomain.com.csr

# The above is equivalent to the following (for non password-protected key):
openssl req -nodes -new -newkey rsa:2048 -keyout mydomain.com.key -out mydomain.com.csr

# Sign certificate using the mydomain csr with our root CA cert and key
openssl x509 -req -in mydomain.com.csr -CA serverCA.crt -CAkey serverCA.key -CAcreateserial -out mydomain.com.crt -days 1825 -sha256

Generate Client Certs for mutual TLS

Generate Self-Signed Client Root CA (see above)

The Client Root CA (with the private key) need be configured in the broker.

# Create a client certificate client authenticate with and a request to be signed by your root CA.
openssl req -nodes -new -newkey rsa:2048 -keyout client.key -out client.csr

# Sign this certificate using client CSR with our root CA cert and key.
openssl x509 -req -in client.csr -CA clientCA.crt -CAkey clientCA.key -CAcreateserial -out client.crt -days 1825 -sha256

ACL Substitution Variables

Substitution variables are a feature of ACLs that can be helpful for deployments that have a lot of connecting clients (for example, IoT deployments may have thousands or hundreds of thousands of clients) where you may want to configure ACL rules so that those clients can only:

  • publish to topics containing their own client username or MQTT client ID (to prevent a client from impersonating another client)

  • subscribe to topics containing their own client username or MQTT client ID (to prevent a client from receiving data that is intended for another client)

Example of topic exceptions in ACL could be device/$client-username/> to allow publish or subscribe to topics starting with device/$client-username/status or device/$client-username/telemetry. See here for more details.

Client Certificate Authorization

By default, when using client certificates, the common name (CN) in a client certificate’s subject is used as the client username. If no client username has been provisioned, the event broker will attempt to apply the client username named default and the associated client and ACL profile. Note that the substitution variable for $client-username for ACL will still be the common name and NOT default.

The client username default cannot be deleted. To be secure by default, the associated ACL profile should should be as restrictive as possible.

This client username can be 'blacklisted' by creating a client username which is not enabled.

Note that there is a limit of 100 client username for each Message VPN.

Alternatively, client certificates authentication can be configured to allow API provided username. Similarly, if no username or an invalid username is provided, the client username named default will be applied and the substitution variable for $client-username for ACL will still be evaluated to certificate common name.

This is not recommended as any client with the client certificate (and key) can connect as any arbitrary username (which will be used subsequently for authorization).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment