private void addTemporalState(final PlanBDoc doc) {
        final KeyPrefix prefix = getKeyPrefix();
        if (prefix != null) {
            final Instant time = this.time != null
                    ? this.time
                    : this.effectiveTime;
            if (time == null) {
                error(LogUtil.message("Temporal state 'time' is null for {}", mapName));

            } else {
                LOGGER.trace("Putting key {} into table {}", prefix, mapName);
                final TemporalKey k = TemporalKey
                        .builder()
                        .prefix(prefix)
                        .time(time)
                        .build();
                final Val v = getVal();
                catchLmdbError(() -> writer.addTemporalState(doc, new TemporalState(k, v)));
            }
        }
    }
This method applies a post processing function if we are currently within
a function element. At this stage we should have details of the function
to apply from the corresponding start element and content to apply it to
from the characters event.

@param uri       The element's Namespace URI, or the empty string.
@param localName The element's local key, or the empty string.
@param qName     The element's qualified (prefixed) key, or the empty string.
@throws SAXException The client may throw an exception during processing.
@see AbstractXMLFilter#endElement(String,
String, String)
stroom-state/stroom-planb-impl/src/main/java/stroom/planb/impl/pipeline/PlanBFilter.java