Find your dream job at PaperCut

Choose your language

Choose your login

Contact us

Help Center menu

PRODUCT MANUALS

PaperCut NG & PaperCut MF Manual

PRODUCTS FEATURED

Device script API reference

Device scripts are segments of code that run when either a user logs in to a device, a print job is released at the device, or a copy, scan, or fax job has been completed. The script is defined using the concept of a “hook”. A hook is a JavaScript function that is defined by you, the script writer. It is also commonly referred to as an entry point or method. A number of device hooks (entry points) are available and each differ by the point in the workflow when they are called. For example, a hook early in the workflow has the ability to influence behavior later in the flow, while scripts late will correspondingly have access to additional information that would not be available earlier.

Script hooks (entry points)

The available device hooks are:

Device workflow hooks
HookDescription
deviceLoginHook(inputs, actions)

Use this hook for either:

  • Determining any access rights that are normally set on login (i.e. color copy).

  • Setting configuration changes that will apply to the rest of the login session (filter shared accounts).

Point of Call: Immediately after a user has entered their login credentials/PIN/card swipe for authentication.

Limitations: Cannot analyze any jobs (copy/scan/fax/ held print jobs) at this point.

Use cases for this hook Generally, use this hook for any "Session" actions such as:

  • Block login

  • Prevent users from performing color copy

  • Filtered shared accounts for the rest of the login session

deviceJobLogHook(inputs, actions)

Use this hook to analyze and process a copy/fax/scan job after the job has been completed. Think of it as a post job processing hook that allows you to change the job's properties (ie change the cost, add a comment).

Point of Call: Once the device has sent through a list of job logs for processing.

Limitations: This hook can't be used to block device function jobs (as the job has already finished).

Use cases:

  • Color copy quotas for students at a school that wants to block their students from doing large amounts of color copying.

  • Encourage the use of specific devices for color printing by charging a different amount per device (for example, discount the cost on the devices you want users to use).

devicePrintReleaseHook(inputs, actions)

Use this hook to analyze and block release of held print jobs at the device.

Point of Call: Immediately after the user tries to release held print job(s) at the device.

Limitations:

  • This hook can only be used to perform print job analysis and block the release of held jobs

  • This hook only blocks print release jobs that are released from this MFD. However, users can still release jobs via Mobile Print Release, a Release Station, or the User web interface. If you use this hook, you should disable all other release interfaces.

Use case: Prevent the release of jobs charged to a particular account at some devices. For example, a University could prevent the release of jobs charged to the Arts department from any printer outside the Arts building.

All hooks have access to user, device, and utilities information. In addition, each hook has access to specific information, such as device job information for deviceJobLogHook. The scripts have access to these through the two function arguments:

  • inputs - access to the job, user, and device information. inputs are read-only and any modification to variables do not affect the job.

  • actions - Access to perform actions that can influence the job processing, e.g. tochange the job cost. All actions (also known as side-effects) must be performed via the available actions.

All available inputs and actions are listed below.

Script Inputs

User Info (inputs.user)

User Info Script Reference (inputs.user)
Property/MethodDescription
inputs.user.username

(string) The username of the user that has logged into the device.

inputs.user.fullName

(string) The full name of the user who has logged into the device.

inputs.user.email

(string) The email address of the user that has logged into the device.

inputs.user.office

(string) The office of the user that has logged into the device.

inputs.user.department

(string) The department of the user that has logged into the device.

inputs.user.restricted

(boolean) Determines if the user is restricted.

inputs.user.balance

(number) The user's current account balance.

inputs.user.getBalance(accountName)

(number) The user's current account balance. When a user has multiple personal accounts, the user's current account balance.

Parameters:

  • accountName (string) -This is an optional parameter to specify the personal account name. If not specified, it retrieves the user's total account balance.

inputs.user.isInGroup(groupName)

Determines if the user belongs to the given group name (as defined on the Groups tab).

Parameters:

  • groupName (string) - The name of the group to check. NOTE: The group name is case-sensitive.

inputs.user.getProperty(propName)

Return a value as a string associated with a persistent custom-defined property saved on the user, or null if there is no such value.

Parameters:

  • propName (string) - The name/key of a user property to look up.

For more information about using storage properties, see Custom-defined persistent properties (storage).

inputs.user.getNumberProperty(propName)

A convenience method to return a value as a number associated with a persistent custom-defined property saved on the user, or null if there is no such value.

Parameters:

  • propName (string) - The name/key of a user property to look up.

For more information about using storage properties, see Custom-defined persistent properties (storage).

inputs.user.defaultSharedAccountName

(string) Gets the default shared account name for a user (if configured). If not configured, returns an empty string ("").

inputs.user.autoChargeToSharedAccountName

(string) If the user has an autocharge to shared account, returns the name of that shared account. If there is no autocharge to shared account, returns an empty string ("").

inputs.user.canChargeToPersonalAccount

(boolean) Determines if the user can charge to their personal account. Device and printer overrides supersede this setting.

inputs.user.canOnlyChargeToPersonalAccount

(boolean) Determines if the user can charge only to their personal account (ie if the Account Selection setting in the Admin web interface is:

  • Automatically charge to personal account

  • Charge to personal account with confirmation.

Device and printer overrides supersede this setting.

inputs.user.canSelectSharedAccount

(boolean) Determines if the user has permission to select a shared account.

inputs.user.canSelectAccountFromList

(boolean) Determines if the user can select a shared account from a list. Device and printer overrides supersede this setting.

inputs.user.canSelectAccountUsingPin

(boolean) Determines if the user can select a shared account using PIN codes. Device and printer overrides supersede this setting.

inputs.user.isInternal

(boolean) Determines if the user is an internal user.

inputs.user.primaryCardNumber

(string) Returns the primary card number if configured. If not configured, returns an empty string ("").

inputs.user.secondaryCardNumber

(string) Returns the secondary card number if configured. If not configured, returns an empty string ("").

inputs.user.cardPin

(string) Returns the card PIN for a user if configured. If not configured, returns an empty string ("").

Device Info (inputs.device)

Device Info Script Reference (inputs.device)
Property/MethodDescription
inputs.device.serverName

(string) The name of the server where the device is hosted.

inputs.device.deviceName

(string) The name of the device.

inputs.device.fullDeviceName

(string) The full name of the device in the format server/device.

inputs.device.isDisabled

(boolean) Determines if this device is currently disabled.

inputs.device.groups

(Array) An array of all the device groups that this device is a member of.

inputs.device.isInGroup(groupName)

(boolean) Determines if the device belongs to a particular device group.

Parameters:

  • groupName (string) - The name of the printer group to check.

inputs.device.getProperty(propName)

Return a value as a string associated with a persistent custom-defined property saved on the device, or null if there is no such value.

Parameters:

  • propName (string) - The name/key of a device property to look up.

For more information about using storage properties, see Custom-defined persistent properties (storage).

inputs.device.getNumberProperty(propName)

A convenience method to return a value as a number associated with a custom-defined property saved on the device, or null if there is no such value.

Parameters:

  • propName (string - The name/key of a device property to look up.

For more information about using storage properties, see Custom-defined persistent properties (storage).

Utilities (inputs.utils)

Utilities Script Reference (inputs.utils)
MethodDescription
inputs.utils.formatBalance(amount)

Formats the balance amount based on the server currency settings. Returns a string.

Parameters:

  • amount (number) - the amount to format.

inputs.utils.formatCost(amount)

Formats the cost amount (e.g. a job cost) based on the server currency settings.

Returns a string.

Parameters:

  • amount (number) - the amount to format.

inputs.utils.formatNumber(amount, decimals)

Formats a number with the given number of decimal places.

Returns a string.

Parameters:

  • amount (number) - the amount to format.

  • decimals (number) - The number of decimal places to format.

inputs.utils.getProperty(propName)

Return a value as a string associated with a persistent custom-defined global property, or null if there is no such value.

Parameters:

  • propName (string) - The name/key of a global property to look up.

For more information about using storage properties, see Custom-defined persistent properties (storage).

inputs.utils.getNumberProperty(propName)

A convenience method to return a value as a number associated with a persistent custom-defined global property, or null if there is no such value.

Parameters:

  • propName (string) - The name/key of a global property to look up.

For more information about using storage properties, see Custom-defined persistent properties (storage).

Device Job Info (inputs.job)

Device Job Info Script Reference (inputs.job)
Property/MethodDescription
inputs.job.copies

(number) The number of copies. The totalPages attribute already takes the copies into account.

inputs.job.date

(date) The date/time of the copy, scan, or fax job.

inputs.job.paperSizeName

(string) The paper size name (e.g. Letter, Tabloid, A4, A3).

inputs.job.isGrayscale

(boolean) Determines if the copy, scan, or fax job is grayscale (i.e. contains no color).

inputs.job.isColor

(boolean) Determines if the copy, scan, or fax job is color (i.e. contains at least one color page).

inputs.job.isDuplex

(boolean) Determines if the copy, scan, or fax job is duplex.

inputs.job.totalGrayscalePages

(number) The total number of grayscale pages in the copy, scan, or fax job.

inputs.job.totalColorPages

(number) The total number of color pages in the copy, scan, or fax job.

inputs.job.totalPages

(number) The total number of pages in the copy, scan, or fax job.

inputs.job.totalSheets

(number) The total number of sheets of paper produced by the copy, scan, or fax job.

inputs.job.selectedSharedAccountName

(string) The full name of the selected shared account. If no shared account is selected then an empty string is returned ("").

inputs.job.username

(string) The username of the user that performed the copy, scan, or fax job.

inputs.job.isSimplex

(boolean) Determines if the copy, scan, or fax job is simplex.

inputs.job.isFax

(boolean) Determines if it's a fax job.

inputs.job.isScan

(boolean) Determines if it's a scan job.

inputs.job.isCopy

(boolean) Determines if it's a copy job.

inputs.job.duplexPages

(number) The number of duplex pages.

inputs.job.isInvoiced

(boolean) Determines if the copy, scan, or fax job is invoiced.

inputs.job.cost

(number) The cost of the job. The cost returned is the cost of the job after all other cost adjustments have been applied.

inputs.job.calculateCostForDevice(deviceName)

(number) Calculates the cost of this job on another device. This can be used in combination with actions.job.setCost to first calculate the job using another cost model and then applying a new cost.

This returns the cost of the job.

Parameters:

  • deviceName (string) - The name of the device to calculate the cost of the job for. Enter the device name only (without the server name).

inputs.job.comment

(string) The comment for the copy, scan, or fax job.

inputs.job.documentName

(string) The document name.

Held job Info (inputs.heldJob)

Held Job Info Script Reference (inputs.heldJob)
Property/MethodDescription
inputs.heldJob.documentName

(string) Name of the document.

inputs.heldJob.clientMachineOrIP

(string) The machine name or IP address of the client workstation where the job was printed. If both the machine name and the IP address are known, the machine name is returned.

inputs.heldJob.isColor

(boolean) Determines if the job is color (i.e. contains at least one color page).

inputs.heldJob.isDuplex

(boolean) Determines if the job is duplex.

inputs.heldJob.isGrayscale

(boolean) Determines if the job is grayscale (i.e. contains no color).

inputs.heldJob.cost

(number) The cost of the job.

inputs.heldJob.totalPages

(number) The total number of pages in the print job.

inputs.heldJob.printerName

(string) The printer name.

inputs.heldJob.date

(date) The date/time the job was printed.

inputs.heldJob.fullPrinterName

(string) The full name of the printer including the server name, in the format server\printer.

inputs.heldJob.username

(string) The username of the user that printed the job.

inputs.heldJob.selectedSharedAccountName

(string) The full name of the selected shared account. If no shared account is selected then an empty string is returned ("").

inputs.heldJob.isSimplex

(boolean) Determines if the job is simplex.

inputs.heldJob.copies

(number) The number of copies.

inputs.heldJob.printerServerName

(string) The name of the server the print queue is hosted on.

inputs.heldJob.isChargeToPersonalAccount

(boolean)Determines if the job is being charged to personal account.

inputs.heldJob.isChargeToSharedAccount

(boolean) Determines if the job is being charged to a shared account.

inputs.heldJob.isInvoice

(boolean)Determines if the job is being invoiced.

inputs.heldJob.comment

(string) Returns the comment. If there is no comment, an empty string is returned ("").

inputs.heldJob.paperSizeName

(string) The paper size name (e.g. Letter, Tabloid, A4, A3).

Script Actions

User actions (actions.user)

User Actions Script Reference (actions.user)
MethodDescription
actions.user.onCompletionSaveProperty(propName, value[, options])

Creates a custom-defined persistent user property with a specific value. This operation is performed when the hook has finished running.

Parameters:

  • propName (string) - the name/key of the property to set.

  • value (string) - the property value. Note: Numbers are converted to a string.

For more information about using storage properties, see Custom-defined persistent properties (storage).

actions.user.onCompletionIncrementNumberProperty(propName, value[, options])

A convenience method that increments the value of a custom-defined persistent user property. This operation is performed when the hook has finished running.

Parameters:

  • propName (string) - the name/key of the property to set.

  • value (number) - the amount to increment by. A negative number will decrement.

For more information about using storage properties, see Custom-defined persistent properties (storage).

Device actions (actions.device)

Device Actions Script Reference (actions.device)
MethodDescription
actions.device.onCompletionSaveProperty(propName, value[, options])

Creates a custom-defined persistent device property with a specific value. This operation is performed when the hook has finished running.

Parameters:

  • propName (string) - the name/key of the property to set.

  • value (string) - the property value. Note: Numbers are converted to a string.

For more information about using storage properties, see Custom-defined persistent properties (storage).

actions.device.onCompletionIncrementNumberProperty(propName, value[, options])

A convenience method that increments the value of a custom-defined persistent user property. This operation is performed when the hook has finished running.

Parameters:

  • propName (string) - the name/key of the property to set.

  • value (number) - the amount by which to increment. A negative number will decrement.

For more information about using storage properties, see Custom-defined persistent properties (storage).

Utility actions (actions.utils)

Utility Actions Script Reference (actions.utils)
MethodDescription
actions.utils.sendEmail(recipient, subject, body)

Sends an email to an email address or username.

Parameters:

  • recipient (string) - either the email address or username of the email recipient.

  • subject (string) - subject text of the email.

  • body (string) - body text of the email.

actions.utils.sendEmail(recipients, subject, body)

Sends an email to one or many email addresses or usernames.

Parameters:

  • recipients (array of strings) - either the email addresses or usernames of the email recipients.

  • subject (string) - subject text of the email.

  • body (string) - body text of the email.

Example: to send an email to many email addresses or usernames

actions.utils.sendEmail(["Administrator", "support-staff@myuniversity.edu"], "Oh no!","we're out of credit!");

actions.utils.onCompletionSaveProperty(propName, value[, options])

Saves a global value as a string associated with a persistent custom-defined property. This operation is performed once the hook has finished running.

Parameters:

  • propName (string) - the name/key of the property to set.

  • value (string) - the property value. Note: Numbers are converted to a string.

For more information about using storage properties, see Custom-defined persistent properties (storage).

actions.utils.onCompletionIncrementNumberProperty(propName, value[, options])

A convenience method to increment a global number value associated with a persistent custom-defined property. This operation is performed once the hook has finished running.

Parameters:

  • propName (string) - the name/key of the property to set.

  • value (number) - the amount to increment by. A negative number will decrement.

For more information about using storage properties, see Custom-defined persistent properties (storage).

Log Actions (actions.log)

Log Actions Script Reference (actions.log)
MethodDescription
actions.log.info(message)

Logs an informational message to the Application Log.

Parameters:

  • message (string) - the informational message in the Application Log.

actions.log.warning(message)

Logs an warning message to the Application Log.

Parameters:

  • message (string) - the warning message in the Application Log.

actions.log.error(message)

Logs an error message to the Application Log.

Parameters:

  • message (string) - the error message in the Application Log.

actions.log.debug(message)

Logs a message to the server's text-based log file ([app-path]/server/logs/server.log). This is helpful to diagnose problems with device scripts.

Parameters:

  • message (string) - the message to be logged.

Login Actions (actions.login)

Login Actions Script Reference (actions.log)
MethodDescription
actions.login.denyLoginAccess()

Block the user from logging in to the device.

Note: This action takes priority over the bypassLoginFilters action.

actions.login.bypassLoginFilters()

Allows a user to bypass any configured login filters and restrictions and access a device.

Note: This action will not work if the action denyLoginAccess is also called.

actions.login.denyCopyAccess()

Block both color and grayscale copying on login. This feature is not supported for all device types so make sure you test before using in a live environment.

actions.login.denyColorCopyAccess()

Block color copying on login. This feature is not supported for all device types so make sure you test before using in a live environment.

Note: This action takes priority over bypassColorCopyFilters.

actions.login.bypassColorCopyFilters()

Allows a user to bypass any configured color copying filters and restrictions and grants them color copying access.

Note: This action will not work if denyColorCopyAccess if also called.

actions.login.setAvailableSharedAccounts(parentNames)

Restrict the shared accounts available at the device by creating a whitelist of approved accounts. A user who logs into the device can charge only to their shared accounts if those accounts have been whitelisted.

Parameters:

  • parentNames (Array) - A list of parent shared account names.

Note: This action takes effect on the “Account Selection” screen. Please review recipe “Restrict selectable shared accounts on device” to address corner cases.

This action accepts only parent shared accounts. Any child accounts will be implicitly included in the whitelist when the parent account is listed.

Example: To allow for only Science related shared accounts to be selected on the device:

actions.job.setAvailableSharedAccounts( ["Biology", "Chemistry", "Physics"]);

In the above example, a user who belongs to two faculties and can charge to both “Biology” and “Arts” shared accounts, but will only be able to charge to “Biology” when accessing this device (as “Arts” has not been whitelisted).

Job actions (actions.job)

Job Actions Script Reference (actions.job)
MethodDescription
actions.job.setCost (cost)

Sets the cost of the job.

Note: If there are other cost adjustments configured (e.g. user cost overrides), these will be applied before the deviceJobLog hook has started running.

Parameters:

  • cost (number) - The cost of the job. Must be greater than or equal to 0.

actions.job.addComment (comment)

Appends a comment to the job. This is logged to the database and is available in the job logs and reports. If the job already has a comment (e.g. set by the user with the advanced client) then this appends to the existing comment.

Parameters:

  • comment (string) - The comment to add to the print job.

Held Print Job actions (actions.heldJob)

Held Print Job Actions Script Reference (actions.job)
MethodDescription
actions.heldJob.blockRelease(message)

Block the user from releasing a held print job and display a customizable message on the device screen to notify the user as to why the job was blocked from release. If the user releases multiple held print jobs at the same time, then calling this action on at least one of those held print jobs will subsequently block the other jobs from being released.

Parameters:

  • message (string) - The message displayed on the screen when the job gets blocked from release.

actions.heldJob.blockRelease()

Block the user from releasing a held print job. A default message will be displayed on the device screen to notify the user that the held print job was denied due to print restrictions. If the user releases multiple held print jobs at the same time, then calling this action on at least one of those held print jobs will subsequently block the other jobs from being released.

Custom-defined persistent properties (storage)

Device scripts have the ability to store or save information between executions. They allow you to implement advanced logic that takes advantage of not just the current job event information, but any information that has been stored by previous script events. Properties can also be used to share data between different scripts. Some ideas that can be implemented with device script properties include:

  • Rate limits – knowledge of previous jobs in the given period need to be stored/known.

  • Detecting duplicate events/situations over time.

  • Detecting repeatable user behavior. e.g. how many times a user uses duplex in a row.

  • Shared settings between scripts . e.g. Global defined configuration variables/settings.

Properties are key-value pair storage that are associated with a user or device, or optionally can be global. Keys are Strings that uniquely define the property. Values are stored as strings and are any data that can be converted to and from a string. The maximum length of a key is 70 characters, and the value is 1,000 characters.

Working with properties

Properties are fetched via the getProperty call on the associated source. For example, to fetch a property stored for:

  • the user associated with the login or job (depending on the hook), use inputs.user.getProperty("my-key")

  • the device, use inputs.device.getProperty(),

  • global properties, use inputs.utils.getProperty().

There is also a set of convenience methods called getNumberProperty() if dealing exclusively with a number.

By default, properties are saved (to the database) only after the hook is completed.

You can also set the values of properties. For example, to set a property on the user, use:

actions.user.onCompletionSaveProperty("my-key", "my-value")

Implementing Counters (Advanced)

There are two ways to implement a counter (e.g. a page number count). One approach is to get the current value, increment, then save. However, on high volume networks, another event might overwriting the value. Device scripts provide a convenient method that avoids this called onCompletionIncrementNumberProperty(). See the recipe “Impose a daily color copy limit” for an example.

Device script requirements (advanced)

These notes are intended for advanced developers “pushing the limits” of device script functionality. All device scripts must conform to the following technical requirements:

  1. Timeouts: All scripts’ execution logic should complete within 5 seconds of CPU time. Failure to comply (for example, due to an infinite loop), results in the script terminating and raising a runtime error. Five seconds is adequate as even the most advanced example recipes complete within a few milliseconds.

  2. Idempotent: All scripts should remain idempotent. It’s expected to provide the same output given the same input. Side-effects based off logic other than the inputs are not recommended. For example, logic based off the result of Math.random() would violate this principle.

Device Script Frequently Asked Questions

Will device scripting be available for all device types?

Device scripting is supported on all platforms, however certain devices may not support all the device hooks (for example, deviceJobLogHook) or all of the actions (for example, disabling color copy). We strongly recommend testing your device script before applying it in production. For more information, see Known issues with device scripting or contact PaperCut Support or your local reseller.

What happens if a user reaches their daily color copying limit in the middle of a job?

The daily color copying limit script is triggered when a user logs into the device. This means that if a user is part way through a job when the limit is reached, the job will still continue copying in color. Next time the user logs into the device, they will not be able to do color copying.

Comments