public void storeWorkflowDefinition(
      AbstractWorkflowDefinition<? extends WorkflowState> definition) {
    StoredWorkflowDefinition storedDefinition = convert(definition);
    MapSqlParameterSource params = new MapSqlParameterSource();
    params.addValue("type", definition.getType());
    String serializedDefinition = serializeDefinition(storedDefinition);
    params.addValue("definition_sha1", sha1(serializedDefinition));
    params.addValue("definition", serializedDefinition, sqlVariants.longTextType());
    params.addValue("modified_by", executorInfo.getExecutorId());
    params.addValue("executor_group", executorInfo.getExecutorGroup());

    String sql =
        "update nflow_workflow_definition "
            + "set definition = :definition, modified_by = :modified_by, definition_sha1 = :definition_sha1 "
            + "where type = :type and executor_group = :executor_group and definition_sha1 <> :definition_sha1";
    int updatedRows = namedJdbc.update(sql, params);
    if (updatedRows == 0) {
      sql =
          "insert into nflow_workflow_definition(type, definition_sha1, definition, modified_by, executor_group) "
              + "values (:type, :definition_sha1, :definition, :modified_by, :executor_group)";
      try {
        namedJdbc.update(sql, params);
      } catch (DataIntegrityViolationException dex) {
        logger.debug("Another executor already stored the definition.", dex);
      }
    }
  }
 public List<StoredWorkflowDefinition> queryStoredWorkflowDefinitions(Collection<String> types) {
   String sql =
       "select definition from nflow_workflow_definition where "
           + executorInfo.getExecutorGroupCondition();
   MapSqlParameterSource params = new MapSqlParameterSource();
   if (!isEmpty(types)) {
     sql += " and type in (:types)";
     params.addValue("types", types);
   }
   return namedJdbc.query(
       sql,
       params,
       new RowMapper<StoredWorkflowDefinition>() {
         @Override
         public StoredWorkflowDefinition mapRow(ResultSet rs, int rowNum) throws SQLException {
           return deserializeDefinition(rs.getString("definition"));
         }
       });
 }