Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -146,4 +146,12 @@ private FormConstants() {
/** The resource type for date time input field v1 */
public static final String RT_FD_FORM_DATETIME_V1 = RT_FD_FORM_PREFIX + "datetime/v1/datetime";

/** The resource type for the Adobe Sign fields datasource (Electronic Signature tab) */
public static final String RT_FD_FORM_ADOBESIGN_FIELDS_DATASOURCE_V1 = RT_FD_FORM_PREFIX
+ "container/v2/container/datasource/adobesignfields";

/** The resource type for the generic form-fields datasource (email/phone/countrycode autocomplete) */
public static final String RT_FD_FORM_FIELDS_DATASOURCE_V1 = RT_FD_FORM_PREFIX
+ "container/v2/container/datasource/formfields";

}
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
package com.adobe.cq.forms.core.components.internal.models.v2.form;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
Expand All @@ -33,7 +35,12 @@
import org.apache.sling.models.annotations.Default;
import org.apache.sling.models.annotations.Exporter;
import org.apache.sling.models.annotations.Model;
import org.apache.sling.models.annotations.injectorspecific.*;
import org.apache.sling.models.annotations.injectorspecific.ChildResource;
import org.apache.sling.models.annotations.injectorspecific.InjectionStrategy;
import org.apache.sling.models.annotations.injectorspecific.OSGiService;
import org.apache.sling.models.annotations.injectorspecific.Self;
import org.apache.sling.models.annotations.injectorspecific.SlingObject;
import org.apache.sling.models.annotations.injectorspecific.ValueMapValue;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.slf4j.Logger;
Expand All @@ -57,6 +64,7 @@
import com.adobe.cq.forms.core.components.models.form.FormClientLibManager;
import com.adobe.cq.forms.core.components.models.form.FormContainer;
import com.adobe.cq.forms.core.components.models.form.FormMetaData;
import com.adobe.cq.forms.core.components.models.form.SignerInfo;
import com.adobe.cq.forms.core.components.models.form.ThankYouOption;
import com.adobe.cq.forms.core.components.util.AbstractContainerImpl;
import com.adobe.cq.forms.core.components.util.ComponentUtils;
Expand All @@ -66,6 +74,7 @@
import com.day.cq.wcm.api.PageManager;
import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonProperty;
import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;

@Model(
adaptables = { SlingHttpServletRequest.class, Resource.class },
Expand Down Expand Up @@ -159,6 +168,20 @@ public class FormContainerImpl extends AbstractContainerImpl implements FormCont
@Self(injectionStrategy = InjectionStrategy.OPTIONAL)
private AutoSaveConfiguration autoSaveConfig;

/** Electronic Signature — container-level enable flag */
@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "_useSignedPdf")
private boolean useAdobeSign;

/** Electronic Signature — signerInfo child node (contains cloud config, workflow, signers) */
@ChildResource(injectionStrategy = InjectionStrategy.OPTIONAL, name = "signerInfo")
@Nullable
private Resource signerInfoResource;

private String signConfigPath;
private String signingWorkflowType;
private boolean firstSignerFormFiller;
private List<SignerInfo> signers = Collections.emptyList();

@Inject
private ResourceResolver resourceResolver;

Expand Down Expand Up @@ -488,6 +511,61 @@ public AutoSaveConfiguration getAutoSaveConfig() {
return autoSaveConfig;
}

@PostConstruct
private void initSigningConfig() {
if (signerInfoResource != null) {
ValueMap vm = signerInfoResource.getValueMap();
signConfigPath = vm.get("signConfigPath", String.class);
signingWorkflowType = vm.get("workflowType", String.class);
// firstSignerFormFiller is now stored per-signer inside the multifield items
// Signer items are stored as children of signerInfo/signer (multifield)
Resource signerContainer = signerInfoResource.getChild("signer");
if (signerContainer != null) {
List<SignerInfo> signerList = new ArrayList<>();
for (Resource child : signerContainer.getChildren()) {
SignerInfo signer = child.adaptTo(SignerInfo.class);
if (signer != null) {
signerList.add(signer);
}
}
signers = Collections.unmodifiableList(signerList);
}
}
}

@Override
@JsonIgnore
public boolean isUseAdobeSign() {
return useAdobeSign;
}

@Override
@Nullable
@JsonIgnore
public String getSignConfigPath() {
return signConfigPath;
}

@Override
@Nullable
@JsonIgnore
public String getSigningWorkflowType() {
return signingWorkflowType;
}

@Override
@JsonIgnore
public boolean isFirstSignerFormFiller() {
return !signers.isEmpty() && signers.get(0).isFirstSignerFormFiller();
}

@Override
@JsonIgnore
@SuppressFBWarnings(value = "EI_EXPOSE_REP", justification = "signers is already Collections.unmodifiableList")
public List<SignerInfo> getSigners() {
return signers;
}

private Map<String, Object> getSubmitProperties() {

Map<String, Object> submitProps = null;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,182 @@
/*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
~ Copyright 2024 Adobe
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
package com.adobe.cq.forms.core.components.internal.models.v2.form;

import org.apache.sling.api.resource.Resource;
import org.apache.sling.models.annotations.Model;
import org.apache.sling.models.annotations.injectorspecific.InjectionStrategy;
import org.apache.sling.models.annotations.injectorspecific.ValueMapValue;
import org.jetbrains.annotations.Nullable;

import com.adobe.cq.forms.core.components.models.form.SignerInfo;
import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;

@Model(
adaptables = { Resource.class },
adapters = { SignerInfo.class })
public class SignerInfoImpl implements SignerInfo {

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "signerTitle")
@Nullable
private String signerTitle;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "emailSource")
@Nullable
private String emailSource;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "email")
@Nullable
private String email;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "emailAutocomplete")
@Nullable
private String[] emailAutocomplete;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "securityOption")
@Nullable
private String securityOption;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "countryCodeSource")
@Nullable
private String countryCodeSource;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "countryCode")
@Nullable
private String countryCode;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "countryCodeAutocomplete")
@Nullable
private String[] countryCodeAutocomplete;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "phoneSource")
@Nullable
private String phoneSource;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "phone")
@Nullable
private String phone;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "phoneAutocomplete")
@Nullable
private String[] phoneAutocomplete;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "signFieldBlocks")
@Nullable
private String[] signFieldBlocks;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "signerAfFieldsBlock")
@Nullable
private String[] signerAfFieldsBlock;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "firstSignerFormFiller")
private boolean firstSignerFormFiller = false;

@ValueMapValue(injectionStrategy = InjectionStrategy.OPTIONAL, name = "signerNumber")
private int signerNumber = 1;

@Override
@Nullable
public String getSignerTitle() {
return signerTitle;
}

@Override
@Nullable
public String getEmailSource() {
return emailSource;
}

@Override
@Nullable
public String getEmail() {
return email;
}

@Override
@Nullable
@SuppressFBWarnings("EI_EXPOSE_REP")
public String[] getEmailAutocomplete() {
return emailAutocomplete != null ? emailAutocomplete.clone() : null;
}

@Override
@Nullable
public String getSecurityOption() {
return securityOption;
}

@Override
@Nullable
public String getCountryCodeSource() {
return countryCodeSource;
}

@Override
@Nullable
public String getCountryCode() {
return countryCode;
}

@Override
@Nullable
@SuppressFBWarnings("EI_EXPOSE_REP")
public String[] getCountryCodeAutocomplete() {
return countryCodeAutocomplete != null ? countryCodeAutocomplete.clone() : null;
}

@Override
@Nullable
public String getPhoneSource() {
return phoneSource;
}

@Override
@Nullable
public String getPhone() {
return phone;
}

@Override
@Nullable
@SuppressFBWarnings("EI_EXPOSE_REP")
public String[] getPhoneAutocomplete() {
return phoneAutocomplete != null ? phoneAutocomplete.clone() : null;
}

@Override
@Nullable
@SuppressFBWarnings("EI_EXPOSE_REP")
public String[] getSignFieldBlocks() {
return signFieldBlocks != null ? signFieldBlocks.clone() : null;
}

@Override
@Nullable
@SuppressFBWarnings("EI_EXPOSE_REP")
public String[] getSignerAfFieldsBlock() {
return signerAfFieldsBlock != null ? signerAfFieldsBlock.clone() : null;
}

@Override
public boolean isFirstSignerFormFiller() {
return firstSignerFormFiller;
}

@Override
public int getSignerNumber() {
return signerNumber;
}
}
Loading
Loading