How can I save arrays of values in the database? I am trying to save multiple values from a textarea to a database table.

I use the following code, but I feel it is the wrong way. 

foreach ($user_emails as $key =&gt; $value) {
  $insert_banned_emails = db_insert('banned_users');
  $insert_banned_emails
    -&gt;fields(array(
      'email' =&gt; $value,
    ))
    -&gt;execute();
}


Is there a different way for achieving the same result?
I would use the following code.

foreach ($user_emails as $value) {
  $query = db_insert('banned_users');
  $query-&gt;fields(array('email' =&gt; $value))-&gt;execute();
}


Alternatively, you could use the following code.

$query = db_insert('banned_users')-&gt;fields(array('email'));

foreach ($user_emails as $value) {
  $query-&gt;values(array('email' =&gt; $value));
}

$query-&gt;execute();


With MySQL, the query uses the multi-value syntax.

With other databases, the executed queries will be one for each call to $query-&gt;values(), wrapped in a transaction. This means the queries will be rolled back when one of them fails. In fact, the code executed from InsertQuery::execute() is the following one.

  // Each insert happens in its own query in the degenerate case. However,
  // we wrap it in a transaction so that it is atomic where possible. On many
  // databases, such as SQLite, this is also a notable performance boost.
  $transaction = $this-&gt;connection-&gt;startTransaction();

  try {
    $sql = (string) $this;
    foreach ($this-&gt;insertValues as $insert_values) {
      $last_insert_id = $this-&gt;connection-&gt;query($sql, $insert_values, $this-&gt;queryOptions);
    }
  }
  catch (Exception $e) {
    // One of the INSERTs failed, rollback the whole batch.
    $transaction-&gt;rollback();
    // Rethrow the exception for the calling code.
    throw $e;
  }


In short, I would use the code you are using if the inserted values are independent from each other; I would use the code I shown when the values depend from each other.

In your case, the emails are independent from each other. If you would use the second snippet I shown, the database table will contains all the values, when the sub-query don't fail, or none when a single sub-query fails.

You could also use drupal_write_record(), even though I much prefer the other snippets.

foreach ($user_emails as $value) {
  drupal_write_record('banned_users', array('email' =&gt; $value));
}


I don't see any pro in using this snippet, though. 

Reference


Insert queries