BCL easyPDF SDK
easyPDF SDK Usermanual
PDF Creator Programming API  |  Download Free Trial  |  Contact Us to Purchase

Using Impersonation

Impersonation is an alternative to the Loader Service, available in the Native .NET, Java, PHP, Python and C/C++ APIs. Impersonation is not available in the COM API.

If you choose to use Impersonation, the Loader Service does not have to be configured or started at all.

It is very important to understand that Impersonation only works on the server side. While the Loader Service works everywhere, you cannot use the Impersonation technique in a desktop application. This is not a disadvantage, as desktop applications do not require special handling.

Just like the Loader Service, Impersonation also requires the purchase of a special server license. Without this license server-side printing is impossible.

The easiest way to use Impersonation is via the PrinterImpersonator class. Its constructor takes two input arguments, the UserName and the Password, both of which must be explicitly specified. From there, call the LaunchPrinter method to create a Printer object.

Note that both UserName and Password are required and cannot be null or an empty string for server-side operation.

On the other hand, Impersonation cannot be used on the desktop. If you try to use PrinterImpersonator on the desktop, it will fail, except on .NET, where your specified user name and password will just be ignored.

All major SDK objects have their own corresponding impersonator classes:

SDK Impersonator Method
Printer PrinterImpersonator LaunchPrinter
PDFProcessor PDFProcessorImpersonator LaunchPDFProcessor
PDFConverter PDFConverterImpersonator LaunchPDFConverter
PDFDocument PDFDocumentImpersonator LaunchPDFDocument

However, only Printer mandates the use of Loader or Impersonation. The other SDKs should work directly.

The only reason to use Loader or Impersonation with the other SDKs is when your server is running under low privileges, and there is no other way to gain access to certain files or resources. Normally only Printer should be Impersonated.

Considerations for Microsoft Excel 2016 and Microsoft Outlook

Due to a recent software update, the Impersonation API does not work with Microsoft Excel 2016 anymore. Most versions of Microsoft Outlook also fail with the Impersonation API.

Therefore, we recommend the use of the Loader Service instead, especially for those who need to print Excel or Outlook documents.

Configuring an Account for use with Impersonation

Impersonation requires a Local Administrator Account be created on the machine that is running the SDK. Please follow these steps when configuring this User Account;

Native .NET API

Here is the simplest C# example:

PrinterImpersonator impersonator = new PrinterImpersonator("easyPDF8User", "Password");
using(Printer printer = impersonator.LaunchPrinter())
{
   printer.PrintJob.PrintOut(inputFileName, outputFileName);
}

For a little more security, use SecureString instead of string in the second argument. SecureString is a special obfuscated string class that cannot be sniffed so easily.

SecureString password = new SecureString()
password.AppendChar('1');
password.AppendChar('2');
password.AppendChar('3');
password.AppendChar('4');
password.AppendChar('5');
PrinterImpersonator impersonator = new PrinterImpersonator("easyPDF8User", password);
using(Printer printer = impersonator.LaunchPrinter())
{
   printer.PrintJob.PrintOut(inputFileName, outputFileName);
}

Only in .NET, the LaunchPrinter, LaunchPDFProcessor, LaunchPDFConverter and LaunchPDFDocument methods have an optional timeout parameter, which is the maximum number of milliseconds to wait for the worker process. If missing, the default value is 60000 (which is 1 minute). You may very easily override this:

PrinterImpersonator impersonator = new PrinterImpersonator("easyPDF8User", "Password");
using(Printer printer = impersonator.LaunchPrinter(120000))
{
   printer.PrintJob.PrintOut(inputFileName, outputFileName);
}

Native Java API

Here is the simplest Java example:

PrinterImpersonator impersonator = new PrinterImpersonator("easyPDF8User", "Password");
Printer printer = impersonator.LaunchPrinter();
try
{
   printer.getPrintJob().PrintOut(inputFileName, outputFileName);
}
catch(Exception e)
{
   System.out.println(e);
}
finally
{
   printer.dispose();
}

Native PHP API

Here is the simplest PHP5 example:

$impersonator = new BCL\easyPDF\Printer\PrinterImpersonator("easyPDF8User", "Password");
$printer = $impersonator->LaunchPrinter();
try
{
   $printer->getPrintJob()->PrintOut(inputFileName, outputFileName);
}
catch(BCL\easyPDF\Printer\PrinterException $ex)
{
   echo $ex->getMessage(), "\n";
}

Native Python API

Here is the simplest Python3 example:

impersonator = easyPDFPrinter.PrinterImpersonator("easyPDF8User", "Password")
printer = impersonator.LaunchPrinter()
try:
   printer.getPrintJob().PrintOut(inputFileName, outputFileName)
except easyPDFPrinter.PrinterException as ex:
   print(ex)

Security Considerations

Unfortunately there is no way around having to store your easyPDF account password. You have many choices regarding where and how you want to store the password.

Storing your Impersonation password in your source code is not as bad as it sounds. No one can see your source code, unless your server gets hacked. In that case there is no point hiding your password anymore.

The most important thing is to make sure your password is not used anywhere else. Do not use the same password for easyPDF Impersonation that you use for your personal accounts (email, social media, banks). This is very important. If you are using a server-side database, that should have a different password as well.

If your organization requires your password to be encrypted, there are several choices:

All of the above solutions rely on the DPAPI. Unfrotunately, the DPAPI is only really secure when it is bound to a physical user account, which cannot be done on the server side, because the Local System account is not a physical user account.

As a result, it is very important to use a custom entropy, which significantly enhances the strength of the encryption. The problem is that now you have to store the entropy securely, which is just as impossible as securely storing the password itself.

The disadvantage of all forms of encryption is that you have to store the encryption key somewhere, which is not any easier than storing the password itself. If you encrypt the password, you also need to encrypt the encryption key, but then your encryption key that encrypts the encryption key that encrypts the password is still exposed. And no matter how deeply it is nested, some piece of information is always exposed. This is a viscious circle.

The two most important practices are the following:

Note that the Loader Service isn't inherently more secure, either. Internally it uses the same DPAPI as well to store an encrypted password in the registry.