So there I was, happily assisting one of our clients with a mobile signature system, when I got this crazy text:
That was the end of it. My heart sank. My mind reeled. I called up Jonathan Ackerman, the lead developer for the client, and shared with him what LaRona had said.
He thought for a minute and replied, “Here’s what we’ll do. We’ll make a way for a user to sign a form without ever touching the iPad. How about we create a record just for signatures? We can send a link out to the client that will open a WebDirect interface. It would present them their signature record on their own device, and boom! Touch-free signatures.”
“Brilliant!” I said happily. “Let’s go! I’ll grab some pizza.”
Alright – so it may not have happened EXACTLY like that but it was pretty close. We did recently have to invent a way to sign forms on-site without sharing devices and I think Jonathan Ackerman’s solution was as close to perfect as it gets in this business.
We have a two-file freight delivery solution (separation model) that is shared via Claris FileMaker Server 19 and is hosted on a Windows Server Instance from Amazon Web Services. Within the local area network (LAN), it is accessed via FileMaker Pro on desktop, and FileMaker Go on iPad.
On the delivery routes, cell reception can be quite unreliable, especially since much of the delivery work takes place inside of old New York City apartment buildings and warehouses. So the FileMaker Go solution uses API-based sync routines that Jonathan and I developed together to send and receive data to the server.
The basic idea is this: Forms and related data are downloaded to the iPad. As the drivers edit the forms, entries are created in a table called MobileEditLog. It doesn’t matter if there’s a connection to server or not, these edit logs are created. This is the data cache for syncing.
At the end of an edit cycle, the sync system checks for a connection to server. If there’s a connection available, it immediately sends the edits to server. If there is no connection, nothing happens. The MobileEditLogs just sit there until connection is restored.
In the meantime, FileMaker Server has a listening routine that checks for new uploads from the field every minute. If it sees new edits from the field, it will process the edits and update the appropriate fields throughout the system.
Signatures are stored in container fields. They are handled a bit differently for sync (see this example), but are fields nonetheless. So we’re still dealing with field-level data and not anything radical.
The primary problem was simple: how can we get a signature from any device the signer might have? A secondary problem arose when we discussed implementing a public-facing file: protecting the main system from any accidental or nefarious access because of some security oversight on our part.
The general workflow we needed looked like this:
1. The driver touches a button that generates an email to the end user.
2. The end user taps or clicks a link and their web browser opens the web direct page with their form.
3. The end user signs.
4. The signature is applied to the form.
5. A PDF is emailed to the end user.
6. The next time the driver syncs, the signature is shown on the mobile form
While an FM Data API web app may have worked equally well, the speed and ease of development of WebDirect made it the obvious answer here. Being browser-based and platform-agnostic, deployment would be simple as well. Presenting the signer with a WebDirect record and a simple signing user interface would also make the load time very small as an extra bonus. Of course, this would require some concurrent licensing choices. For this particular client, we had good data on how many mobile signatures were happening concurrently on average on any given day, so it was pretty easy to determine what we needed.
To solve any security issues before they arose, we decided on creating a third file completely detached from the main system. This way records would only be created at the time of signing and deleted as soon as they were collected by server. The total number of records at any given time would be the total number of clients signing at that moment.
Since we already had a listener script running every minute, we attached the signature processing script to the end of the listener process. When the script ran it processed all the MobileEditLogs that had been uploaded to server, then processed any signatures that had been signed, and then deleted those temporary signature records.
The actual workflow ended up looking like this:
This process has been field tested and we are super happy with the results. Our client can now offer safer signing to their customers and it gives them an edge in the marketplace when courting new business. Let’s take a look at how to build something like this.
Security
Again, we felt that it would be most secure to keep this file separate from the main file since it will be exposed to the internet via a WebDirect connection. For simplicity we allow for a guest account so no login is needed for the end user— just a WebDirect URL with the form ID as a parameter.
The guest login does not need a username/password, which would be too cumbersome for the end user. It has no privileges outside of opening the file. When the “On First Window” script trigger runs, the guest is immediately re-logged in as a different privilege set – “web user” – when Get (SystemPlatform) = 4 (which is WebDirect). In this way, we accomplished our security goals: minimal exposure and minimal access coupled with ease of use for the user.
Forms Layout
First we built the needed layout for the end user with a PDF container with the unsigned form for viewing, a text field for the signer’s name, and the web viewer with the JavaScript signature library.
Multi-Page PDF Work-Around
One issue we immediately discovered was that in WebDirect a container field can only show a multi-page PDF on a desktop web browser. The forms that our clients are signing are multi-page PDFs, so we had to figure out how to display these in mobile browsers (iPad, iPhone, Android).
We ended up creating a child table called ‘Form Pages’ to store a separate record for each page of the PDF version of the Form. This afforded the user the ability to scroll between pages before signing. So we built another table called ‘Form Pages’ that is related to the primary Forms record. This ultimately meant creating one layout per platform type, but that actually worked to our benefit. We needed separate layouts for each device anyway to allow for sizing issues and as shown below in part 3.
Javascript Library
In order to allow for signing from any device, we utilized a JavaScript drawing library that we found on another blog which simply displays a signing box with a save button. Users can sign using mouse or gestures depending on the device. When the “save” button is clicked or tapped, a script is called that inserts the image into a container field.
Note that the web viewer object must have the “Allow Javascript to interact with client” selection enabled. Then we added the new FileMaker script object FileMaker.PerformScript (script, params) to the original JavaScript that calls the process signature script after the user touches the save button.
Once the elements for signature capture were in place, we needed a script on the server that could be called from the iPad (technician in the field) to generate a new record, grab the form ID and email the link to the end user.
Since the FileMaker Go file is designed for offline use in a city environment where there is often no cell service or WiFi, we needed a way to call a script on the server even if there is no consistent connection. We utilized the Data API Script Endpoint:
Insert From URL ($ServerAddress & $DatabaseName & “/layouts/” & $LayoutName & “/script/” & $script &”?script.param=” & $param)
$ServerAddress is the FQDN (fully qualified domain name) of the server
$DatabaseName is just the name portion of the database filename, with no extension
$LayoutName is the context from which the script should be called
$script is the script name (in our case it was ‘Get Form’)
$param are any script parameters (in our case the form ID)
This script resides in the main file of the solution. It, in turn, reaches out to our new mobile signature file as necessary to both create a record for signing and retrieving signatures after signing.
Before calling the script endpoint we grab a new token that is required for authentication. If there is an issue retrieving the token it is likely there is no current connection and the user is alerted.
The script creates a new record in the Forms file, grabs the record ID, saves a PDF copy of the form, and builds the WebDirect link that the end user will need to connect to their form, which looks like:
https://{serverDomain}/fmi/webdirect/{Filename}?script={ScriptName}¶m=” & {Parameter} & “& homeurl={URL to return when file is closed}
IMPORTANT: You must have a valid SSL certificate installed for this process to work properly and not just the temporary certificate installed with FMS.
In our case the script (in the Forms file that the webdirect link will call) simply grabs the ID sent as a parameter and finds the correct form record.
Note the additional ‘homeurl’ parameter. After the user signs the WebDirect form, they are alerted with a dialog that the signature was received and, after closing the dialog, the file is closed. Without a ‘homeurl’ they would be returned to the WebDirect home page. With the ‘homeurl’ element, you can direct them to any webpage you please. In our case it goes to the client’s home page. A nice feature!
The script then sends an email message with the link as an email to the end user. You must use send as SMTP since this is running on server.
The one caveat here is that since you are calling the script via the API there is no connection to the file system, meaning the API is not treated as a user with access to the operating system. So you must call a secondary script via Perform Script On Server (PSoS), which is able to generate a PDF. Think of Perform Script On Server as “Perform Script As The Server User”, and it makes more sense. What the API can’t do, PSoS can.
When the end user taps or clicks the emailed link, the ‘Find Forms’ script is called in the Forms file and they are directed to their record. In order to provide the most security (so any rogue actors could not see any other forms that are still available), we locked down the Forms table in security settings by allowing the connected user to view only their form and no others.
The link sent via email has an ID parameter that is used to identify the user’s record in the signature file. When the user clicks the link, it opens the signature file as explained above and performs a find for that ID. It then presents the multiple pages of the form so that the user can confirm the shipment and the fine print.
The emailed link looks like this:
https://fm.serveraddress.com/fmi/webd/webforms?script=YourScriptName¶m= DF966C8A-A88B-4476-A59B-9D5B95C56DBB& homeurl=http://www.portagebay.com
The link explained:
The server address for WebDirecthttps://fm.serveraddress.com/fmi/webd/webforms?
The script with the parameterscript=YourScriptName¶m=DF966C8A-A88B-4476-A59B-9D5B95C56DBB
The landing page&homeurl=http://www.portagebay.com
To be clear, if you’re building this for your own solution, replace fm.serveraddress.com with your server address; replace YourScriptName with the name of the script you want to run to perform the find; and replace the parameter with the ID of the record you want to find. Anything after “param=“ is passed like a parameter in FileMaker Pro, so use whatever technique you normally use for passing parameters.
As mentioned, the layout the user is directed to contains three objects – a container field with the PDF of the form that requires a signature, a text field for entering their name and the web viewer populated with a JavaScript library for drawing. The JavaScript essentially allows the user to draw their signature and touch ‘Save’, which runs a script to capture the signature and store it in a container field. The function is triggered when the user clicks ‘Save’ in the web viewer.
When the ‘Save’ button is clicked in the web viewer, a script is called that first grabs a Base64 version of the signature as a parameter, and also updates that status of the form to ‘signed’ so that the signature cannot be overwritten. If no errors occur, a dialog displays that the signature was successfully received and the user is then redirected to the client’s website homepage. If the user tries to re-select the link after successfully signing, they are alerted that the form is already signed.
Now that the signature has been inserted into a container field in the Forms table, a scheduled script runs every minute on the server and checks for any records with ‘Signed’ status. If it finds a signed form, the signed name and signature data is uploaded to the main data file. An email is sent to the end user with a signed version of their form. The record in the Forms table is then deleted since it is no longer needed.
The final piece of the puzzle was for the ‘off-line’ mobile techs in the field to view the signature on their device so that they can confirm successful signing. The scheduled script that processes the signed forms creates an edit log record for this updated field value, like any other edit on desktop. When the user touches the Sync button, the script queries the server for all edits that have not been downloaded by that specific user, downloads them, and processes them. The updated signature simply becomes one of those edits.
The core piece – the signature layout – was not too difficult to get working; making the whole process work from initial signature request to receiving the signature ended up being a complex series of pieces that had to work well together. The fact is, not only is it possible to work around LaRona’s interruptions, but doing so is only going to make us better at what we do.
In collaboration with:
Portage Bay Solutions is assisting Jonathan Ackerman in this project who is the lead developer and original creator of the system referenced in this post. Jonathan has been an independent FileMaker developer since January 1998 and version 3. He has developed solutions for nonprofits, municipalities and businesses in industries such as logistics, event management, healthcare, public relations and law. He particularly enjoys helping clients solve challenging business processes through great solutions utilizing the latest innovations in technology. He has toured as a classical pianist on 3 continents and 40 states. Jonathan currently resides in Irvington, NY, just outside of New York City where he lives with his wife and 18 year old son. He enjoys music, the outdoors and golf.
If you would like us to bring our expertise to your project as well, then submit your details below. We would love to discuss your software development needs with you.
Very cool. Thank you for sharing 🙂
And thank you for reading!
Your email address will not be published. Required fields are marked *
Comment *
Name
Email
Website
Save my name, email, and website in this browser for the next time I comment.
Post Comment