2.3.3. Create Update Function

This section describes the update function based on an example application.

Description of the function to be created
  1. Click the project ID in the project list.
../../../../../_images/project_update_detail_link.png
  1. Click the “Change(変更)” button on the target project’s detail screen.
../../../../../_images/project_update_detail.png
  1. Rewrite the item to be updated and click the Update (更新) button.
../../../../../_images/project_update_update.png
  1. When the update confirmation screen is displayed, click on the confirm (確定) button.
../../../../../_images/project_update_confirm.png
  1. The database is updated and the update completion screen is displayed.
../../../../../_images/project_update_complete.png

2.3.3.1. Enter and confirm update contents

Of the implementation methods of the update function, the input and confirmation of the update contents are described in the following order.

Create a form

Create a form to accept parameters for transitioning from detail screen to update screen and a form to accept input values for edit field of update screen.

A form to accept parameters when transitioning from the detail screen to the update screen

Create a form to accept the target project ID which is passed as a path parameter ( ”:projectId” part of “show/:projectId”) when transitioning from the detail screen to the update screen.

ProjectTargetForm.java
public class ProjectTargetForm implements Serializable {

    /** Project ID */
    @Required
    @Domain("id")
    private String projectId;

    // Getter and setter are omitted
A form that accepts values entered from the update screen

Create a form to accept the value entered from the update screen after editing.

ProjectUpdateForm.java
public class ProjectUpdateForm implements Serializable {

    // Partial excerpt

    /** Project name */
    @Required
    @Domain("projectName")
    private String projectName;

    /**
     * Acquire the project name.
     *
     * @return Project name
     */
    public String getProjectName() {
        return this.projectName;
    }

    /**
     * Set the project name.
     *
     * @param projectName Project name to be set
     */
    public void setProjectName(String projectName) {
        this.projectName = projectName;
    }
}
Key points of this implementation
  • Although the input items are duplicated with the project registration screen, the form for the project update screen should be created since form should be created for each HTML form for responsibility assignment.
Create a business action method to display the update screen

Create a business action method that retrieves the current information from the database and displays the update screen.

ProjectAction.java
@InjectForm(form = ProjectTargetForm.class)
public HttpResponse edit(HttpRequest request, ExecutionContext context) {

    // Delete the session information used in the update process.
    SessionUtil.delete(context, "project");

    ProjectTargetForm targetForm = context.getRequestScopedVar("form");
    LoginUserPrincipal userContext = SessionUtil.get(context, "userContext");

    // Throws a NoDataException if the target project has been deleted by another user
    ProjectDto dto = UniversalDao.findBySqlFile(ProjectDto.class, "FIND_BY_PROJECT",
            new Object[]{targetForm.getProjectId(), userContext.getUserId()});

    // Set the output information to the request scope
    context.setRequestScopedVar("form", dto);

    SessionUtil.put(context, "project", BeanUtil.createAndCopy(Project.class, dto));

    return new HttpResponse("/WEB-INF/view/project/update.jsp");
}
Key points of this implementation
Create a JSP for the update screen
Screen creation has been described in Create Initial Display of Registration Screen in the registration section and is omitted.
Create a business action method to check the updated contents

Create a business action method that validates the update content and displays the confirmation screen. In addition to Bean Validation, the validation with database search is implemented in the business action method.

ProjectAction.java
@InjectForm(form = ProjectUpdateForm.class, prefix = "form")
@OnError(type = ApplicationException.class,
        path = "/WEB-INF/view/project/update.jsp")
public HttpResponse confirmOfUpdate(HttpRequest request, ExecutionContext context) {
    ProjectUpdateForm form = context.getRequestScopedVar("form");

    // Search the database to check if there are any customers with the entered ID
    if (form.hasClientId()) {
        if (!UniversalDao.exists(Client.class, "FIND_BY_CLIENT_ID",
                new Object[] {Integer.parseInt(form.getClientId()) })) {
                    throw new ApplicationException(
                        MessageUtil.createMessage(MessageLevel.ERROR,
                            "errors.nothing.client", form.getClientId()));

        }
    }

    Project project = SessionUtil.get(context, "project");

    // Overwrite a form value to a session
    BeanUtil.copy(form, project);

    // Set the output information to the request scope
    context.setRequestScopedVar("form", BeanUtil.createAndCopy(ProjectDto.class, form));
    context.setRequestScopedVar("profit", new ProjectProfit(
            project.getSales(),
            project.getCostOfGoodsSold(),
            project.getSga(),
            project.getAllocationOfCorpExpenses()
    ));

    return new HttpResponse("/WEB-INF/view/project/confirmOfUpdate.jsp");
}
Key points of this implementation
Create SQL

Create SQL to acquire customer information from customer IDs to confirm the existence of a customer.

client.sql
FIND_BY_CLIENT_ID =
SELECT
    CLIENT_ID,
    CLIENT_NAME,
    INDUSTRY_CODE
FROM
    CLIENT
WHERE
    CLIENT_ID = :clientId
Key points of this implementation
  • The SQL for existence confirmation is made as a SELECT statement.
Create a JSP for the update confirmation screen

Create an update confirmation screen by reusing the update screen.

/src/main/webapp/WEB-INF/view/project/update.jsp
<n:form useToken="true">
  <!-- Confirmation of registration -->
    <div class="title-nav page-footer">
        <!-- Button at the bottom of the page -->
        <div class="button-nav">
            <n:forInputPage>
                <!-- Button for input screen -->
            </n:forInputPage>
            <n:forConfirmationPage>
                <!-- Button for confirmation screen -->
                <n:submit value = "Confirm" uri="/action/project/update" id="bottomSubmitButton"
                        cssClass="btn btn-raised btn-success"
                        allowDoubleSubmission="false" type="button" />
            </n:forConfirmationPage>
        </div>
    </div>
</n:form>
Key points of this implementation

2.3.3.2. Database update

Among the implementation methods of update function, confirmation of update content is explained in the following order.

Create a business action method

Create a business action method to update the database and finalize the changes. The entity definition for performing optimistic lock is also explained.

Create a business action method for database update

Create a business action method to update the database and redirect to the completion screen display method.

ProjectAction.java
@OnDoubleSubmission
public HttpResponse update(HttpRequest request, ExecutionContext context) {
    Project targetProject = SessionUtil.delete(context, "project");
    UniversalDao.update(targetProject);

    return new HttpResponse(303, "redirect://completeOfUpdate");
}
Key points of this implementation
  • Sets the values you want to update to an entity and updates the database using UniversalDao#update. In the update process, optimistic locking is performed.
  • Assign @OnDoubleSubmission to prevent duplicate form submission.
  • Redirect the response to prevent a rerun in the browser update.
Create an entity for optimistic locking

Create an entity with optimistic lock enabled.

Project.java
// Other properties are omitted

/** Version number */
private Long version;

/**
 * Returns the version number.
 *
 * @return Version number
 */
@Version
@Column(name = "VERSION", precision = 19, nullable = false, unique = false)
public Long getVersion() {
    return version;
}

/**
 * Set the version number.
 *
 * @param version Version number
 */
public void setVersion(Long version) {
    this.version = version;
}
Key points of this implementation
Create a business action method to display the completion screen

Create a business action method that displays the completion screen, which is the redirect destination of the update method.

ProjectAction.java
public HttpResponse completeOfUpdate(HttpRequest request, ExecutionContext context) {
    return new HttpResponse("/WEB-INF/view/project/completeOfUpdate.jsp");
}
Create an update completion screen

Creates an update completion screen.

/src/main/webapp/WEB-INF/view/project/completeOfUpdate.jsp
<n:form>
    <div class="title-nav">
        <h1 class="page-title">Project change completion screen</h1>
        <div class="button-nav">
          <!-- Omitted -->
        </div>
    </div>
    <div class="message-area message-info">
        Project update is now complete.
    </div>
    <!-- Omitted -->
</n:form>

This completes the description of the update function.

Getting Started To TOP page