Projet

Général

Profil

Paste
Télécharger (6,33 ko) Statistiques
| Branche: | Révision:

root / drupal7 / sites / all / modules / flag / includes / flag / flag_comment.inc @ 59e46405

1
<?php
2

    
3
/**
4
 * @file
5
 * Contains the flag_comment class.
6
 */
7

    
8
/**
9
 * Implements a comment flag.
10
 */
11
class flag_comment extends flag_entity {
12
  function options() {
13
    $options = parent::options();
14
    $options += array(
15
      'access_author' => '',
16
    );
17
    return $options;
18
  }
19

    
20
  /**
21
   * Options form extras for comment flags.
22
   */
23
  function options_form(&$form) {
24
    parent::options_form($form);
25

    
26
    $form['access']['access_author'] = array(
27
      '#type' => 'radios',
28
      '#title' => t('Flag access by content authorship'),
29
      '#options' => array(
30
        '' => t('No additional restrictions'),
31
        'comment_own' => t('Users may only flag own comments'),
32
        'comment_others' => t('Users may only flag comments by others'),
33
        'node_own' => t('Users may only flag comments of nodes they own'),
34
        'node_others' => t('Users may only flag comments of nodes by others'),
35
      ),
36
      '#default_value' => $this->access_author,
37
      '#description' => t("Restrict access to this flag based on the user's ownership of the content. Users must also have access to the flag through the role settings."),
38
    );
39
  }
40

    
41
  function type_access_multiple($entity_ids, $account) {
42
    $access = array();
43

    
44
    // If all subtypes are allowed, we have nothing to say here.
45
    if (empty($this->types)) {
46
      return $access;
47
    }
48

    
49
    // Ensure node types are granted access. This avoids a
50
    // node_load() on every type, usually done by applies_to_entity_id().
51
    $query = db_select('comment', 'c');
52
    $query->innerJoin('node', 'n', 'c.nid = n.nid');
53
    $result = $query
54
      ->fields('c', array('cid'))
55
      ->condition('c.cid', $entity_ids, 'IN')
56
      ->condition('n.type', $this->types, 'NOT IN')
57
      ->execute();
58
    foreach ($result as $row) {
59
      $access[$row->nid] = FALSE;
60
    }
61

    
62
    return $access;
63
  }
64

    
65
  function get_entity_id($comment) {
66
    // Store the comment object in the static cache, to avoid getting it
67
    // again unneedlessly.
68
    $this->remember_entity($comment->cid, $comment);
69
    return $comment->cid;
70
  }
71

    
72
  /**
73
   * Overrides flag_flag::get_flagging_record().
74
   *
75
   * This queries for flagging records for all comments on the node for the
76
   * current comment, and prefills the flag_get_user_flags() static cache with
77
   * the result for a performance gain.
78
   */
79
  function get_flagging_record($entity_id, $uid = NULL, $sid = NULL) {
80
    static $seen_comment_nids = array();
81

    
82
    $comment = $this->fetch_entity($entity_id);
83

    
84
    // Figure out if this is the first comment we've seen for its parent node.
85
    if (!isset($seen_comment_nids[$comment->nid])) {
86
      // Preload the flag_get_user_flags() static cache with flagging records
87
      // for all the comments on the node. This means that if multiple comments
88
      // on this node are being viewed, only one query is run for all their
89
      // flagging records, rather than one for each comment. This is because
90
      // flag_get_user_flags() can only optimized across flags on one entity.
91
      $flag_get_user_flags_cache = &drupal_static('flag_get_user_flags');
92

    
93
      // We need to get a row for each comment, including empty ones if there is
94
      // no flagging, so that the cache is warmed up for all comments. Therefore
95
      // the query has to have the {comment} table as its base, and include the
96
      // comment cid field.
97
      $query = db_select('comment', 'c');
98
      $query->leftJoin('flagging', 'f',
99
        "c.cid = f.entity_id AND f.entity_type = 'comment'");
100
      $query->fields('f')
101
        ->fields('c', array('cid'))
102
        ->condition('c.nid', $comment->nid)
103
        ->condition(db_or()
104
          // We want to include rows for comments which have no flaggings at all
105
          // for the current user.
106
          ->isNull('f.flagging_id')
107
          // The same conditions as flag_get_user_flags()'s query.
108
          ->condition(db_and()
109
            ->condition(db_or()
110
              ->condition('f.uid', $uid)
111
              ->condition('f.uid', 0)
112
            )
113
            ->condition('f.sid', $sid)
114
          )
115
        );
116

    
117
      // The result set can have multiple rows for a single comment, and rows
118
      // which have no flagging ID, so there's nothing useful to index it by.
119
      $result = $query->execute()->fetchAll();
120

    
121
      $flag_names = _flag_get_flag_names();
122
      foreach ($result as $flagging_data) {
123
        $cid = $flagging_data->cid;
124

    
125
        // At the very least, we need an empty array for the entity ID key in
126
        // the cache array, so it counts as present.
127
        if (!isset($flag_get_user_flags_cache[$uid][$sid]['comment'][$cid])) {
128
          $flag_get_user_flags_cache[$uid][$sid]['comment'][$cid] = array();
129
        }
130

    
131
        // If the flagging table gave us no data, we're done with this row.
132
        if (is_null($flagging_data->flagging_id)) {
133
          continue;
134
        }
135

    
136
        // Remove the comment ID field from the row, so it's just the flagging
137
        // table row.
138
        unset($flagging_data->cid);
139

    
140
        $flag_get_user_flags_cache[$uid][$sid]['comment'][$cid][$flag_names[$flagging_data->fid]] = $flagging_data;
141
      }
142

    
143
      // Mark that we've seen this node so we don't process it again.
144
      $seen_comment_nids[$comment->nid] = TRUE;
145
    }
146

    
147
    // Return data for the comment we were asked about.
148
    $user_flags = flag_get_user_flags($this->entity_type, $entity_id, $uid, $sid);
149
    return isset($user_flags[$this->name]) ? $user_flags[$this->name] : NULL;
150
  }
151

    
152
  function get_labels_token_types() {
153
    return array_merge(array('comment', 'node'), parent::get_labels_token_types());
154
  }
155

    
156
  function replace_tokens($label, $contexts, $options, $entity_id) {
157
    if ($entity_id) {
158
      if (($comment = $this->fetch_entity($entity_id)) && ($node = node_load($comment->nid))) {
159
        $contexts['node'] = $node;
160
        $contexts['comment'] = $comment;
161
      }
162
    }
163
    return parent::replace_tokens($label, $contexts, $options, $entity_id);
164
  }
165

    
166
  function get_flag_action($entity_id) {
167
    $flag_action = parent::get_flag_action($entity_id);
168
    $comment = $this->fetch_entity($entity_id);
169
    $flag_action->content_title = $comment->subject;
170
    $flag_action->content_url = $this->_flag_url("comment/$comment->cid", "comment-$comment->cid");
171
    return $flag_action;
172
  }
173

    
174
  function get_relevant_action_objects($entity_id) {
175
    $comment = $this->fetch_entity($entity_id);
176
    return array(
177
      'comment' => $comment,
178
      'node' => node_load($comment->nid),
179
    );
180
  }
181
}