The majority of SavaPage configuration is conducted in the Administrator Web App. Additional configuration
options can be set in the
/opt/savapage/server/server.properties
configuration
file, and with the Config Editor.
Alternative port are set in the
/opt/savapage/server/server.properties
configuration file as shown in the table below.
Key | Description |
---|---|
|
Server http port. Default:
|
|
Server https port. Default:
|
|
Redirect HTML of non-SSL port to SSL:
|
|
The RAW Print Server port. Default:
|
Table 13.5. Server Properties: Alternative TCP/IP Ports
Since SavaPage is run by user
savapage
, you can't use ports
below 1024, because these ports can only be bound to by the
superuser (root). If you want SavaPage Web Apps to be
accessible through port 80 and 443 at all costs, you can use Apache or NGINX server to forward (or "reverse-proxy") requests to
SavaPage.
A high reliability server process like SavaPage must reject excess requests immediately (fail fast) by using a Request Queue with a bounded capacity.
When a request is rejected, the user browser will show a diagnostic message, for example that “The connection to the server was reset while the page was loading” because “The site could be temporarily unavailable or too busy”, with the advise to “Try again in a few moments”.
Request Queue capacity is calculated according to a tolerable “no-response” time.
For example, if the server is capable of handling 100 requests per second,
and 30 seconds of patience is accepted by users in the event of excessive
high load, you can set the queue capacity to
30*100=3000
.
If queue capacity is set too low, the server will reject requests too soon and won't be able to handle normal load spikes. If set too high, a high load, that exceeds the processing power of the server application, will continue to stack requests on the queue. And thus, even after the load stops, the application will appear to have stopped responding to new requests as it still has lots of requests on the queue to handle.
Requests are FIFO processed by threads contained in a ThreadPool. The
maximum number of threads needed, in order to achieve the best performance,
depends on host resources (RAM and CPU cores) assigned to the SavaPage
application. The maximum value will typically be between
50
and 500
.
The keys to set thread pool and queue capacity in the
/opt/savapage/server/server.properties
configuration file are shown in the table below.
Key | Description |
---|---|
|
The capacity (maximum length) of the queue holding
client requests to the server. Requests are FIFO
processed by threads in the pool. Default:
|
|
Maximum number of threads in the pool. Default:
|
|
Minimum number of threads in the pool. Default:
|
|
Maximum time a thread may be idle in milliseconds
after it is terminated. Default:
|
Table 13.6. Server Properties: ThreadPool Settings
ThreadPool settings are part of application performance tuning. See Chapter 22, Tuning in general and Section 22.1, “Linux Kernel Parameters” in particular.
The browser “connection reset” message can be easily provoked by setting very low threadpool values, like:
server.threadpool.queue.capacity=4 server.threadpool.minthreads=1 server.threadpool.maxthreads=5 server.threadpool.idle-timeout-msec=10000
... and frantically pressing the F5 browser key.
Server Web Sessions expire after a certain period of inactivity: see Section 17.3.1, “Web Session Timeout”. Expired sessions are removed by a cyclic scavenge process. The cycle interval can be set with this property:
Key | Description |
---|---|
|
The interval (seconds) at which expired server
sessions are scavenged. Default:
|
Table 13.7. Server Properties: Session Settings
SavaPage uses the Remote IP address from an HTTP Request as Client IP address. This usually works out well. However, when client requests go through an HTTP Proxy or Load Balancer, the Remote IP address will be the IP address of the proxy or load balancer only. In that case the Remote IP address can't be used to define Devices or to restrict access to SavaPage objects, like Queues, Web Services, etc. To solve this issue you can set the properties below to use the HTPP X-Forwarded-For header to retrieve the correct Client IP address.
Configuration property | Description |
---|---|
webserver.http.header.xff.enable |
Use the X-Forwarded-For (XFF) HTTP header to retrieve
Client IP address. Values: |
webserver.http.header.xff.proxies.allowed |
A CIDR Set of allowed XFF proxies. If empty all proxies are allowed. Default: empty. |
webserver.http.header.xff.debug |
Enable X-Forwarded-For (XFF) HTTP header debugging.
Values: |
Table 13.8. HTTP Configuration Properties
See Section 4.11.14, “Config Editor” on how to set these properties.
Database connections are both expensive to create and maintain over time. Therefore, they are an ideal resource to pool. That is just what SavaPage does, with the help of JDBC Connection Pooling[27].
The keys to set the Connection parameters in the
/opt/savapage/server/server.properties
configuration file are shown in the table below.
Key | Description |
---|---|
|
Maximum number of connections in the pool. Default:
Important: if you are using PostgreSQL as database back-end this value must align with the maximum number of client connections allowed by the database. See Section 13.5.3.1, “PostgreSQL Settings”. |
|
Minimum number of connections in the pool. Default:
|
|
Maximum time a connection may be idle in seconds after it is closed.
Default: |
|
Idle time in seconds before a connection is checked
for timeout. Default: This value must be less than
|
|
Number of prepared SQL statements that will be cached.
Default: Value |
Table 13.9. Database Connection Settings
Database Connection Settings do not apply to the internal database.
PostgreSQL ships with a basic configuration tuned for wide compatibility rather than performance. Depending on available host resources and Database Connection Settings as described in the section above, there is a good chance the default parameters are very undersized.
Tuning Your PostgreSQL Server is an expert job, but there are
two obvious parameters in postgresql.conf
[28] you need to consider:
max_connections
must at least be equal to database.connection.pool.max
plus the value of
superuser_reserved_connections
. For
example:
#---------------------------------------------------------------- # When SavaPage: database.connection.pool.max = 200 # and in this file: superuser_reserved_connections = 3 # and SavaPage is the only process accessing the Database ... #---------------------------------------------------------------- max_connections = 203 # (change requires restart) # Defaults to 3 #superuser_reserved_connections = 3
The shared_buffers
default of 128MB can be
replaced by a higher value, depending on the total RAM in your
system. For
example:
#---------------------------------------------------------------- # System has 16GB RAM, we take a conservative 6.25% ... #---------------------------------------------------------------- #shared_buffers = 128MB # min 128kB # (change requires restart) shared_buffers = 1024MB
A higher value allocates more shared memory during inter-process communication (IPC) between the database server and the requesting client, resulting in speedier data transfer. See PostgreSQL Memory.
Important: restart the database after changing any of these settings.
CUPS notifier is a custom SavaPage binary that pushes printer and print job status events from CUPS to SavaPage server. It is the default CUPS notification method. A pull method can be activated as alternative.
Occasionally the notifier may fail to deliver job state notifications, as
can be seen reported in /var/log/cups/error_log
. Since
a failure can result in no job end states being observed, a heartbeat
monitor pulls print status from CUPS for active jobs that have not been
notified since the previous beat of the heart. The heartbeat period can be
configured: see Section 13.5.4.4, “CUPS Configuration Properties”.
CUPS Job Status is handled in the following way:
Normally a print job that is stopped in CUPS, for instance because “job-completed-with-errors”, must be manually controlled (reprint, cancel, move) by an operator. However, when SavaPage identifies a stopped job it cancels it automatically.
At system (application) start-up, job status is pulled from CUPS for every proxy printed document that has not reached end-state.
See Section 13.5.4.4, “CUPS Configuration Properties” on how to change the defaults.
See Section 13.5.4.4, “CUPS Configuration Properties” on how to change defaults for the number of IPP connections to local CUPS and their IPP connect and read timeouts.
Configuration property | Description |
---|---|
cups.ipp.notification.method |
CUPS event notification method. Value
|
cups.ipp.notification.push.notify-lease-duration |
Duration of the subscription lease (seconds) for
|
cups.ipp.notification.push.heartbeat-msec |
Number of milliseconds to wait before evaluating pushed CUPS job status notifications. Default: 4000. |
cups.ipp.notification.push.pull-fallback-msec |
Number of milliseconds since the last pushed print job status notification by CUPS Notifier after which a job status update is pulled from CUPS. Default: 30000. |
cups.ipp.notification.pull.heartbeat-msec |
Number of milliseconds to wait before pulling CUPS job status. Default: 5000. |
cups.ipp.job-state.cancel-if-stopped.enable |
Set to Y (default) or N, to enable/disable automatic cancellation of stopped CUPS Job Status. |
system.startup.cups.ipp.sync-print-jobs.enable |
Set to Y (default) or N, to enable/disable CUPS Job Status synchronization at system start-up. |
cups.ipp.local-connect-timeout-msec |
IPP connect timeout in milliseconds on local CUPS. Default: 5000. |
cups.ipp.local-socket-timeout-msec |
IPP read timeout in milliseconds on local CUPS. Default: 9000. |
cups.ipp.max-connections |
Max number of IPP connections on CUPS. Default: 10. |
Table 13.10. CUPS Configuration Properties
See Section 4.11.14, “Config Editor” on how to set these properties.
A Web Page or Document can be printed by a Drag & Drop of its URL. In that case its content is server-side downloaded and rendered as PDF.
Configuration property | Description |
---|---|
download.connect-timeout-msec |
Timeout in milliseconds until a connection is established. Default: 4000. |
download.socket-timeout-msec |
Timeout in milliseconds to receive data from remote host after the connection is established, i.e. maximum time of inactivity between two data packets. Default: 2000. |
download.max-connections |
Max number of download connections. Default: 10. |
download.max-connections-per-route |
Max number of download connections per route (host) Default: 2. |
Table 13.11. Server-side Download Configuration Properties
See Section 4.11.14, “Config Editor” on how to set these properties.
Rendering a Web Page by a Drag & Drop of its URL gives best results when wkhtmltopdf is installed.
When SavaPage makes RESTful API calls to third-party servers, for instance in the IPP Routing Plug-in, these are the configuration properties to consider.
Configuration property | Description |
---|---|
restful.client.connect-timeout-msec |
Timeout in milliseconds until a connection is established. Default: 4000. |
restful.client.read-timeout-msec |
Timeout in milliseconds to receive data from remote host after the connection is established, i.e. maximum time of inactivity between two data packets. Default: 2000. |
restful.client.max-connections |
Max number of RESTful client. Default: 100. |
restful.client.max-connections-per-route |
Max number of RESTful client connections per route (host) Default: 20. |
restful.client.trust-self-signed |
Trust self-signed certificate of RESTful servers: N (default) or Y. |
Table 13.12. RESTful Client Configuration Properties
See Section 4.11.14, “Config Editor” on how to set these properties.
When Document expiration time is enabled, any SafePages document older than the number of configured minutes is considered expired and will be automatically deleted in an active User Web App session. Moreover, when a user logs out and logs in again, expired documents will be auto-deleted. So, when a user does not log in for a long time, old documents will stay put in the user's home directory. These ignored documents take up unnecessary space. The same applies to PDF documents that exist long after their due date, because their deletion is triggered far too late (never) at Fast Print or Hold Print release.
During Daily Maintenance user home directories are scanned and ignored documents deleted. The result of the scan is shown in the Admin Dashboard. These are the configuration properties to consider:
Configuration property | Description |
---|---|
print-in.job-expiry-ignored.mins |
Number of minutes added to print-in job expiry (if applicable) after which job is considered ignored. Ignored jobs are removed by Daily Maintenance. Default: 10. |
proxy-print.hold-ignored-mins |
Number of minutes added to Hold Print job expiry after which job is considered ignored. Ignored jobs are removed by Daily Maintenance. Default: 10. |
Table 13.13. User Home Clean Configuration Properties
See Section 4.11.14, “Config Editor” on how to set these properties.
User Home Clean is also executed at server start-up. You can disable this behavior in a separate Server Setting.
When using an External Database, table row locking is used to serialize access to individual user resources. Production grade databases like PostgreSQL should be able to handle row locking without problems. However, if you do suspect problems in this area, please contact SavaPage support. In the meantime, you can disable row locking with the property below.
Configuration property | Description |
---|---|
webapp.user.database-user-row-locking.enabled |
Enable user table row locking in database to serialize access of a user to database or user home file system: Y (default) | N. |
Table 13.14. Database Locking Configuration Properties
See Section 4.11.14, “Config Editor” on how to set these properties.
SavaPage uses pdftocairo to create PNG images from SafePages. On centos-release-7-7.1908.0.el7, pdftocairo 0.26.5 fails due to a bug. Therefore pdftocairo -v is executed at server start-up to determine the best way to create images. If version is 0.26.5 is encountered workaround statements are applied. This default probe strategy can be overwritten with this configuration property:
Configuration property | Description |
---|---|
system.host.cmd.pdftocairo.img.strategy |
Strategy for executing |
Table 13.15. pdf2cairo Image Strategy Configuration Property
See Section 4.11.14, “Config Editor” on how to set these properties.
To separate files created at runtime from installation files you can set alternative locations for temporary
files, SafePages, public Letterheads and Document
Store in the
/opt/savapage/server/server.properties
configuration file.
All alternative file locations must reside on the same disk partition[29].
Key | Description |
---|---|
|
Location of temporary files created by SavaPage. It is created when the application starts and removed when stopped, so make sure it is exclusively used by the SavaPage application. The location is not used by third-party Java
components: they use Default:
|
|
Location where the user's SafePages are stored. Default:
|
|
Location where the public Letterheads are stored. Default:
|
|
Location where the Archive branch of the Document Store is stored. Default:
|
|
Location where the Journal branch of the Document Store is stored. Default:
|
Table 13.16. Server Properties for Alternative File Locations
These are the extra settings that can be configured in the
/opt/savapage/server/server.properties
configuration file.
Key | Description |
---|---|
|
Enable database cleanup at server start-up. See Section 4.11.12, “Backups”. Values: |
|
Enable User Home Clean at server start-up. Values: |
Put User Home Clean in test mode: i.e. cleanable files are signaled on the Admin Dashboard but not deleted. Values: | |
|
Organization name of Visitor without a Community Member Card. See Section 23.1, “Visitor Period”. |
|
See Section 20.1.1.4, “Custom i18n”. Values: |
Table 13.17. Server Properties: Miscellaneous Settings
Instead of using
/opt/savapage/server/server.properties
to
configure SavaPage, the same keys from the properties file can also be
used as enviroment variables, as follows:
# Namespace as prefix for envvar names (mandatory) SAVAPAGE_NS=SP_ # Required if run in Docker container SP_CONTAINER=DOCKER # server.properties equivalents, for example: SP_server.port=8080 SP_server.ssl.port=8443 # etc ...
Environment variables take precedence over those configured in
/server/server.properties
[27] SavaPage uses Java Database Connectivity (JDBC) Connection Pooling from c3p0: an easy-to-use library for making traditional JDBC drivers “enterprise-ready”.
[28] On Debian based systems postgresql.conf
is
located in
/etc/postgresql/[version]/main/
[29] This constraint is needed because files are initially created in the temporary location and atomically moved to their destination. Atomic moves do not work cross-partition.