1 | <?php |
---|
2 | |
---|
3 | /** |
---|
4 | * @file |
---|
5 | * Admin page callbacks for the trigger module. |
---|
6 | */ |
---|
7 | |
---|
8 | /** |
---|
9 | * Build the form that allows users to assign actions to hooks. |
---|
10 | * |
---|
11 | * @param $type |
---|
12 | * Name of hook. |
---|
13 | * @return |
---|
14 | * HTML form. |
---|
15 | */ |
---|
16 | function trigger_assign($type = NULL) { |
---|
17 | // If no type is specified we default to node actions, since they |
---|
18 | // are the most common. |
---|
19 | if (!isset($type)) { |
---|
20 | drupal_goto('admin/build/trigger/node'); |
---|
21 | } |
---|
22 | if ($type == 'node') { |
---|
23 | $type = 'nodeapi'; |
---|
24 | } |
---|
25 | |
---|
26 | $output = ''; |
---|
27 | $hooks = module_invoke_all('hook_info'); |
---|
28 | foreach ($hooks as $module => $hook) { |
---|
29 | if (isset($hook[$type])) { |
---|
30 | foreach ($hook[$type] as $op => $description) { |
---|
31 | $form_id = 'trigger_'. $type .'_'. $op .'_assign_form'; |
---|
32 | $output .= drupal_get_form($form_id, $type, $op, $description['runs when']); |
---|
33 | } |
---|
34 | } |
---|
35 | } |
---|
36 | return $output; |
---|
37 | } |
---|
38 | |
---|
39 | /** |
---|
40 | * Confirm removal of an assigned action. |
---|
41 | * |
---|
42 | * @param $hook |
---|
43 | * @param $op |
---|
44 | * @param $aid |
---|
45 | * The action ID. |
---|
46 | * @ingroup forms |
---|
47 | * @see trigger_unassign_submit() |
---|
48 | */ |
---|
49 | function trigger_unassign($form_state, $hook = NULL, $op = NULL, $aid = NULL) { |
---|
50 | if (!($hook && $op && $aid)) { |
---|
51 | drupal_goto('admin/build/trigger/assign'); |
---|
52 | } |
---|
53 | |
---|
54 | $form['hook'] = array( |
---|
55 | '#type' => 'value', |
---|
56 | '#value' => $hook, |
---|
57 | ); |
---|
58 | $form['operation'] = array( |
---|
59 | '#type' => 'value', |
---|
60 | '#value' => $op, |
---|
61 | ); |
---|
62 | $form['aid'] = array( |
---|
63 | '#type' => 'value', |
---|
64 | '#value' => $aid, |
---|
65 | ); |
---|
66 | |
---|
67 | $action = actions_function_lookup($aid); |
---|
68 | $actions = actions_get_all_actions(); |
---|
69 | |
---|
70 | $destination = 'admin/build/trigger/'. ($hook == 'nodeapi' ? 'node' : $hook); |
---|
71 | |
---|
72 | return confirm_form($form, |
---|
73 | t('Are you sure you want to unassign the action %title?', array('%title' => $actions[$action]['description'])), |
---|
74 | $destination, |
---|
75 | t('You can assign it again later if you wish.'), |
---|
76 | t('Unassign'), t('Cancel') |
---|
77 | ); |
---|
78 | } |
---|
79 | |
---|
80 | function trigger_unassign_submit($form, &$form_state) { |
---|
81 | $form_values = $form_state['values']; |
---|
82 | if ($form_values['confirm'] == 1) { |
---|
83 | $aid = actions_function_lookup($form_values['aid']); |
---|
84 | db_query("DELETE FROM {trigger_assignments} WHERE hook = '%s' AND op = '%s' AND aid = '%s'", $form_values['hook'], $form_values['operation'], $aid); |
---|
85 | $actions = actions_get_all_actions(); |
---|
86 | watchdog('actions', 'Action %action has been unassigned.', array('%action' => $actions[$aid]['description'])); |
---|
87 | drupal_set_message(t('Action %action has been unassigned.', array('%action' => $actions[$aid]['description']))); |
---|
88 | $hook = $form_values['hook'] == 'nodeapi' ? 'node' : $form_values['hook']; |
---|
89 | $form_state['redirect'] = 'admin/build/trigger/'. $hook; |
---|
90 | } |
---|
91 | else { |
---|
92 | drupal_goto('admin/build/trigger'); |
---|
93 | } |
---|
94 | } |
---|
95 | |
---|
96 | /** |
---|
97 | * Create the form definition for assigning an action to a hook-op combination. |
---|
98 | * |
---|
99 | * @param $form_state |
---|
100 | * Information about the current form. |
---|
101 | * @param $hook |
---|
102 | * The name of the hook, e.g., 'nodeapi'. |
---|
103 | * @param $op |
---|
104 | * The name of the hook operation, e.g., 'insert'. |
---|
105 | * @param $description |
---|
106 | * A plain English description of what this hook operation does. |
---|
107 | * @return |
---|
108 | * |
---|
109 | * @ingoup forms |
---|
110 | * @see trigger_assign_form_validate() |
---|
111 | * @see trigger_assign_form_submit() |
---|
112 | */ |
---|
113 | function trigger_assign_form($form_state, $hook, $op, $description) { |
---|
114 | $form['hook'] = array( |
---|
115 | '#type' => 'hidden', |
---|
116 | '#value' => $hook, |
---|
117 | ); |
---|
118 | $form['operation'] = array( |
---|
119 | '#type' => 'hidden', |
---|
120 | '#value' => $op, |
---|
121 | ); |
---|
122 | // All of these forms use the same validate and submit functions. |
---|
123 | $form['#validate'][] = 'trigger_assign_form_validate'; |
---|
124 | $form['#submit'][] = 'trigger_assign_form_submit'; |
---|
125 | |
---|
126 | $options = array(); |
---|
127 | $functions = array(); |
---|
128 | // Restrict the options list to actions that declare support for this hook-op |
---|
129 | // combination. |
---|
130 | foreach (actions_list() as $func => $metadata) { |
---|
131 | if (isset($metadata['hooks']['any']) || (isset($metadata['hooks'][$hook]) && is_array($metadata['hooks'][$hook]) && (in_array($op, $metadata['hooks'][$hook])))) { |
---|
132 | $functions[] = $func; |
---|
133 | } |
---|
134 | } |
---|
135 | foreach (actions_actions_map(actions_get_all_actions()) as $aid => $action) { |
---|
136 | if (in_array($action['callback'], $functions)) { |
---|
137 | $options[$action['type']][$aid] = $action['description']; |
---|
138 | } |
---|
139 | } |
---|
140 | |
---|
141 | $form[$op] = array( |
---|
142 | '#type' => 'fieldset', |
---|
143 | '#title' => t('Trigger: ') . $description, |
---|
144 | '#theme' => 'trigger_display' |
---|
145 | ); |
---|
146 | // Retrieve actions that are already assigned to this hook-op combination. |
---|
147 | $actions = _trigger_get_hook_actions($hook, $op); |
---|
148 | $form[$op]['assigned']['#type'] = 'value'; |
---|
149 | $form[$op]['assigned']['#value'] = array(); |
---|
150 | foreach ($actions as $aid => $description) { |
---|
151 | $form[$op]['assigned']['#value'][$aid] = array( |
---|
152 | 'description' => $description, |
---|
153 | 'link' => l(t('unassign'), "admin/build/trigger/unassign/$hook/$op/". md5($aid)) |
---|
154 | ); |
---|
155 | } |
---|
156 | |
---|
157 | $form[$op]['parent'] = array( |
---|
158 | '#prefix' => "<div class='container-inline'>", |
---|
159 | '#suffix' => '</div>', |
---|
160 | ); |
---|
161 | // List possible actions that may be assigned. |
---|
162 | if (count($options) != 0) { |
---|
163 | array_unshift($options, t('Choose an action')); |
---|
164 | $form[$op]['parent']['aid'] = array( |
---|
165 | '#type' => 'select', |
---|
166 | '#options' => $options, |
---|
167 | ); |
---|
168 | $form[$op]['parent']['submit'] = array( |
---|
169 | '#type' => 'submit', |
---|
170 | '#value' => t('Assign') |
---|
171 | ); |
---|
172 | } |
---|
173 | else { |
---|
174 | $form[$op]['none'] = array( |
---|
175 | '#value' => t('No available actions for this trigger.') |
---|
176 | ); |
---|
177 | } |
---|
178 | return $form; |
---|
179 | } |
---|
180 | |
---|
181 | /** |
---|
182 | * Validation function for trigger_assign_form(). |
---|
183 | * |
---|
184 | * Makes sure that the user is not re-assigning an action to an event. |
---|
185 | */ |
---|
186 | function trigger_assign_form_validate($form, $form_state) { |
---|
187 | $form_values = $form_state['values']; |
---|
188 | if (!empty($form_values['aid'])) { |
---|
189 | $aid = actions_function_lookup($form_values['aid']); |
---|
190 | if (db_result(db_query("SELECT aid FROM {trigger_assignments} WHERE hook = '%s' AND op = '%s' AND aid = '%s'", $form_values['hook'], $form_values['operation'], $aid))) { |
---|
191 | form_set_error($form_values['operation'], t('The action you chose is already assigned to that trigger.')); |
---|
192 | } |
---|
193 | } |
---|
194 | } |
---|
195 | |
---|
196 | /** |
---|
197 | * Submit function for trigger_assign_form(). |
---|
198 | */ |
---|
199 | function trigger_assign_form_submit($form, $form_state) { |
---|
200 | $form_values = $form_state['values']; |
---|
201 | |
---|
202 | if (!empty($form_values['aid'])) { |
---|
203 | $aid = actions_function_lookup($form_values['aid']); |
---|
204 | $weight = db_result(db_query("SELECT MAX(weight) FROM {trigger_assignments} WHERE hook = '%s' AND op = '%s'", $form_values['hook'], $form_values['operation'])); |
---|
205 | db_query("INSERT INTO {trigger_assignments} values ('%s', '%s', '%s', %d)", $form_values['hook'], $form_values['operation'], $aid, $weight + 1); |
---|
206 | // If this action changes a node property, we need to save the node |
---|
207 | // so the change will persist. |
---|
208 | $actions = actions_list(); |
---|
209 | if (isset($actions[$aid]['behavior']) && in_array('changes_node_property', $actions[$aid]['behavior']) && ($form_values['operation'] != 'presave')) { |
---|
210 | // Delete previous node_save_action if it exists, and re-add a new one at a higher weight. |
---|
211 | $save_post_action_assigned = db_result(db_query("SELECT aid FROM {trigger_assignments} WHERE hook = '%s' AND op = '%s' AND aid = 'node_save_action'", $form_values['hook'], $form_values['operation'])); |
---|
212 | if ($save_post_action_assigned) { |
---|
213 | db_query("DELETE FROM {trigger_assignments} WHERE hook = '%s' AND op = '%s' AND aid = 'node_save_action'", $form_values['hook'], $form_values['operation']); |
---|
214 | } |
---|
215 | db_query("INSERT INTO {trigger_assignments} VALUES ('%s', '%s', '%s', %d)", $form_values['hook'], $form_values['operation'], 'node_save_action', $weight + 2); |
---|
216 | if (!$save_post_action_assigned) { |
---|
217 | drupal_set_message(t('You have added an action that changes a the property of a post. A Save post action has been added so that the property change will be saved.')); |
---|
218 | } |
---|
219 | } |
---|
220 | } |
---|
221 | } |
---|
222 | |
---|
223 | /** |
---|
224 | * Display actions assigned to this hook-op combination in a table. |
---|
225 | * |
---|
226 | * @param array $element |
---|
227 | * The fieldset including all assigned actions. |
---|
228 | * @return |
---|
229 | * The rendered form with the table prepended. |
---|
230 | * |
---|
231 | * @ingroup themeable |
---|
232 | */ |
---|
233 | function theme_trigger_display($element) { |
---|
234 | $header = array(); |
---|
235 | $rows = array(); |
---|
236 | if (count($element['assigned']['#value'])) { |
---|
237 | $header = array(array('data' => t('Name')), array('data' => t('Operation'))); |
---|
238 | $rows = array(); |
---|
239 | foreach ($element['assigned']['#value'] as $aid => $info) { |
---|
240 | $rows[] = array( |
---|
241 | filter_xss_admin($info['description']), |
---|
242 | $info['link'] |
---|
243 | ); |
---|
244 | } |
---|
245 | } |
---|
246 | |
---|
247 | if (count($rows)) { |
---|
248 | $output = theme('table', $header, $rows) . drupal_render($element); |
---|
249 | } |
---|
250 | else { |
---|
251 | $output = drupal_render($element); |
---|
252 | } |
---|
253 | return $output; |
---|
254 | } |
---|
255 | |
---|
256 | |
---|
257 | /** |
---|
258 | * Get the actions that have already been defined for this |
---|
259 | * type-hook-op combination. |
---|
260 | * |
---|
261 | * @param $type |
---|
262 | * One of 'node', 'user', 'comment'. |
---|
263 | * @param $hook |
---|
264 | * The name of the hook for which actions have been assigned, |
---|
265 | * e.g. 'nodeapi'. |
---|
266 | * @param $op |
---|
267 | * The hook operation for which the actions have been assigned, |
---|
268 | * e.g., 'view'. |
---|
269 | * @return |
---|
270 | * An array of action descriptions keyed by action IDs. |
---|
271 | */ |
---|
272 | function _trigger_get_hook_actions($hook, $op, $type = NULL) { |
---|
273 | $actions = array(); |
---|
274 | if ($type) { |
---|
275 | $result = db_query("SELECT h.aid, a.description FROM {trigger_assignments} h LEFT JOIN {actions} a on a.aid = h.aid WHERE a.type = '%s' AND h.hook = '%s' AND h.op = '%s' ORDER BY h.weight", $type, $hook, $op); |
---|
276 | } |
---|
277 | else { |
---|
278 | $result = db_query("SELECT h.aid, a.description FROM {trigger_assignments} h LEFT JOIN {actions} a on a.aid = h.aid WHERE h.hook = '%s' AND h.op = '%s' ORDER BY h.weight", $hook, $op); |
---|
279 | } |
---|
280 | while ($action = db_fetch_object($result)) { |
---|
281 | $actions[$action->aid] = $action->description; |
---|
282 | } |
---|
283 | return $actions; |
---|
284 | } |
---|