? streamline_save.patch ? tax-freetag_1.patch Index: modules/taxonomy/taxonomy.module =================================================================== RCS file: /cvs/drupal/drupal/modules/taxonomy/taxonomy.module,v retrieving revision 1.384 diff -u -p -r1.384 taxonomy.module --- modules/taxonomy/taxonomy.module 2 Oct 2007 16:15:56 -0000 1.384 +++ modules/taxonomy/taxonomy.module 25 Oct 2007 23:39:12 -0000 @@ -531,31 +531,9 @@ function taxonomy_node_save($node, $term unset($terms['tags']); foreach ($typed_input as $vid => $vid_value) { - $typed_terms = drupal_explode_tags($vid_value); - - $inserted = array(); - foreach ($typed_terms as $typed_term) { - // See if the term exists in the chosen vocabulary - // and return the tid; otherwise, add a new record. - $possibilities = taxonomy_get_term_by_name($typed_term); - $typed_term_tid = NULL; // tid match, if any. - foreach ($possibilities as $possibility) { - if ($possibility->vid == $vid) { - $typed_term_tid = $possibility->tid; - } - } - - if (!$typed_term_tid) { - $edit = array('vid' => $vid, 'name' => $typed_term); - $status = taxonomy_save_term($edit); - $typed_term_tid = $edit['tid']; - } - - // Defend against duplicate, differently cased tags - if (!isset($inserted[$typed_term_tid])) { - db_query('INSERT INTO {term_node} (nid, vid, tid) VALUES (%d, %d, %d)', $node->nid, $node->vid, $typed_term_tid); - $inserted[$typed_term_tid] = TRUE; - } + $tag_terms = taxonomy_resolve_tags($vid, $vid_value); + foreach ($tag_terms as $term) { + db_query('INSERT INTO {term_node} (nid, vid, tid) VALUES (%d, %d, %d)', $node->nid, $node->vid, $term->tid); } } } @@ -823,20 +801,27 @@ function _taxonomy_term_children($tid) { * Provides a case-insensitive and trimmed mapping, to maximize the * likelihood of a successful match. * - * @param name + * @param $name * Name of the term to search for. + * @param $vid + * Optional vocabulary ID of the term to search for. * - * @return + * @return $terms * An array of matching term objects. */ -function taxonomy_get_term_by_name($name) { - $db_result = db_query(db_rewrite_sql("SELECT t.tid, t.* FROM {term_data} t WHERE LOWER(t.name) LIKE LOWER('%s')", 't', 'tid'), trim($name)); - $result = array(); - while ($term = db_fetch_object($db_result)) { - $result[] = $term; +function taxonomy_get_term_by_name($name, $vid = NULL) { + if ($vid) { + $result = db_query(db_rewrite_sql("SELECT t.tid, t.* FROM {term_data} t WHERE t.vid = %d AND LOWER(t.name) LIKE LOWER('%s')", 't', 'tid'), $vid, trim($name)); + } + else { + $result = db_query(db_rewrite_sql("SELECT t.tid, t.* FROM {term_data} t WHERE LOWER(t.name) LIKE LOWER('%s')", 't', 'tid'), trim($name)); + } + $terms = array(); + while ($term = db_fetch_object($result)) { + $terms[] = $term; } - return $result; + return $terms; } /** @@ -1163,3 +1148,55 @@ function taxonomy_hook_info() { ), ); } + +/** + * Resolve user input for a free-tagging vocabulary to pre-existing terms. If + * no term exists, optionally create a new term with that name or alternatively, + * return an array of resolvable and unresolvable terms. + * + * @param $vid + * The vid of the vocabulary whose terms are being resolved. + * @param $typed_terms + * An array of free-tagging terms. + * @param $auto_create + * A boolean indicating if new terms can be created if an input term does not + * exist. + * + * @return $tag_terms + * If $auto_create is set to TRUE, returns an array with keys 'old' and 'new' + * containing existing term objects and newly provided term strings + * respectively. If FALSE, returns an array of term objects. + */ +function taxonomy_resolve_tags($vid, $typed_terms, $auto_create = TRUE) { + $typed_terms = taxonomy_explode_tags($typed_terms); + $tag_terms = $auto_create ? array() : array('old' => array(), 'new' => array()); + + foreach ($typed_terms as $typed_term) { + $terms = taxonomy_get_term_by_name($typed_term, $vid); + if ($auto_create) { + if (empty($terms)) { + // Add term to vocabulary. + $term = array('vid' => $vid, 'name' => $typed_term); + taxonomy_save_term($term); + // $tag_terms is an array of term _objects_. As a result, $term array + // needs to be cast into an object. + $tag_terms[$term['tid']] = (object) $term; + } + else { + $tag_terms[$terms[0]->tid] = $terms[0]; + } + } + else { + // New terms are saved in string form. Existing terms are saved as term + // objects. + if (empty($terms)) { + $tag_terms['new'][] = $typed_term; + } + else { + $tag_terms['old'][$terms[0]->tid] = $terms[0]; + } + } + } + + return $tag_terms; +}