You are viewing a plain text version of this content. The canonical link for it is here.
Posted to users@tapestry.apache.org by George Christman <gc...@cardaddy.com> on 2014/05/05 18:13:59 UTC

5.4 Stateless AaxFormLoop

Hi All, I'm trying to create a stateless ajaxformloop using 5.4 and
hibernate, however I appear to be running into a few problems. Code sample
below


@Entity
@Indexed
@Table(name = "employee_profile", uniqueConstraints =
        @UniqueConstraint(columnNames = {"empId", "userProfileId"}))
public class EmployeeProfile extends AbstractProfileEntity {
    //Other non related properties exist but have been removed for this
example.

    @OneToMany(
            mappedBy = "employeeProfile",
            cascade = CascadeType.ALL,
            orphanRemoval = true)
    private List<ProfileEffortAllocation> effortAllocations;

    public List<ProfileEffortAllocation> getEffortAllocations() {
        if (effortAllocations == null) {
            effortAllocations = new ArrayList<>();
        }
        return effortAllocations;
    }

    public void setEffortAllocations(List<ProfileEffortAllocation>
effortAllocations) {
        this.effortAllocations = effortAllocations;
    }

}



@Entity
public class ProfileEffortAllocation extends AbstractEffortAllocation {

    @ManyToOne
    @JoinColumn(
            name = "employee_profile_id",
            nullable = false)
    private EmployeeProfile employeeProfile;

    /**
     *
     */
    public ProfileEffortAllocation() {
    }

    /**
     *
     * @param employeeProfile
     */
    public ProfileEffortAllocation(EmployeeProfile employeeProfile) {
        this.employeeProfile = employeeProfile;
    }

    /**
     *
     * @return
     */
    public EmployeeProfile getEmployeeProfile() {
        return employeeProfile;
    }

    /**
     *
     * @param employeeProfile
     */
    public void setEmployeeProfile(EmployeeProfile employeeProfile) {
        this.employeeProfile = employeeProfile;
    }

}




<div t:type="AjaxFormLoop" t:source="employeeProfile.effortAllocations"
t:value="effortAllocation" t:encoder="encoderEffortAllocation" class="row
even" addRow="block:addRowActivityCodes">
                    <div class="col-xs-6"><div><t:textfield
t:id="activityCode" value="effortAllocation.activityCode"
t:validate="required, maxLength=10"/></div></div>
                    <div class="col-xs-3"><div><t:textfield
t:id="percentOfEffort" value="effortAllocation.percentOfEffort"
t:validate="required,min=0"/></div></div>
                    <t:removerowlink
class="col-xs-3">remove</t:removerowlink>
</div>



@PageActivationContext
private EmployeeProfile employeeProfile;

public void onPrepare() {
    if(employeeProfile == null) {
         employeeProfile = new EmployeeProfile();
    }
}

public void onSuccess() {
        System.out.println("onsuccss");
        alertManager.alert(Duration.TRANSIENT, Severity.INFO, "Employee
profile updated.");
        genericDAO.saveOrUpdate(employeeProfile);
}

ProfileEffortAllocation onAddRow() {
    return new ProfileEffortAllocation(employeeProfile);
}

void onRemoveRow(ProfileEffortAllocation effortAllocation) {
    if(effortAllocation.getId() != null) {
        employeeProfile.getEffortAllocations().remove(effortAllocation);
    }
}

public ValueEncoder<ProfileEffortAllocation> getEncoderEffortAllocation() {
        return new ValueEncoder<ProfileEffortAllocation>() {
            @Override
            public String toClient(ProfileEffortAllocation v) {
                return v.getId() != null ? v.getId().toString() : null;
            }

            @Override
            public ProfileEffortAllocation toValue(String toValue) {
                System.out.println(toValue);
                if (toValue != null) {
                    for (ProfileEffortAllocation effortAllocation :
employeeProfile.getEffortAllocations()) {
                        if (effortAllocation.getId() != null) {
                            Long id = Long.parseLong(toValue);

                            if (id.equals(effortAllocation.getId())) {
                                return effortAllocation;
                            }
                        }
                    }
                }

                ProfileEffortAllocation effortAllocation = new
ProfileEffortAllocation(employeeProfile);

employeeProfile.getEffortAllocations().add(effortAllocation);
                return effortAllocation;
            }
        };
    }


Issues,
1. I can't return null in my encoder toValue without getting the following
exception
Unable to convert client value '2222' back into a server-side object.

2. a. When I add a new row with AjaxFormLoop
    b. return new ProfileEffortAllocation object in toValue
    c. have a null value within a required field in the tml
    d. A validation error is triggered

    toClient is now returning an id rather than null. I'm not sure why this
is happening. Every save with a validation error increments the id.

3. I can't remove existing ProfileEffortAllocations without creating a list
of ProfileEffortAllocations and storing the removed objects in the session
until save.

Does anybody know of a better way to handle this without the use of a
session?

-- 
George Christman
www.CarDaddy.com
P.O. Box 735
Johnstown, New York