@Override
    public String toString() {
        String toStringSql = sql;
        try {
            int index = toStringSql.indexOf('?');
            int count = 0;

            while (index > -1) {
                Object param = params.get(count);
                int type = types.get(count);
                String val = switch (type) {
                    case Types.INTEGER -> "" + param;
                    case Types.BIGINT  -> "" + param;
                    case Types.VARCHAR -> '\'' + (String) param + '\'';
                    case Types.BOOLEAN -> "" + param;
                    default -> null;
                };

                toStringSql = toStringSql.substring(0, index) + val +
                        ((index == toStringSql.length() -1) ? "" : toStringSql.substring(index + 1));
                index = toStringSql.indexOf('?', index + val.length());
                count++;
            }
        }
        catch (Exception e) {
            Log.error(e.getMessage(), e);
        }

        return "CachedPreparedStatement{ sql=" + toStringSql + '}';
    }
Sets all parameters on the given PreparedStatement. The standard code block
for turning a CachedPreparedStatement into a PreparedStatement is as follows:

<pre>
PreparedStatement pstmt = con.prepareStatement(cachedPstmt.getSQL());
cachedPstmt.setParams(pstmt);
</pre>

@param pstmt the prepared statement.
@throws java.sql.SQLException if an SQL Exception occurs.
xmppserver/src/main/java/org/jivesoftware/database/CachedPreparedStatement.java