Skip to content

Commit e84f337

Browse files
committed
Add first pass at admin UI
1 parent 211eaa9 commit e84f337

File tree

3 files changed

+386
-0
lines changed

3 files changed

+386
-0
lines changed

admin.php

Lines changed: 309 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,309 @@
1+
<?php
2+
/**
3+
* Administration UI and utilities
4+
*/
5+
6+
add_action( 'admin_menu', 'json_oauth_admin_register' );
7+
add_action( 'admin_init', 'json_oauth_admin_prerender' );
8+
9+
add_action( 'admin_action_json-oauth-add', 'json_oauth_admin_edit_page' );
10+
add_action( 'admin_action_json-oauth-edit', 'json_oauth_admin_edit_page' );
11+
12+
add_action( 'personal_options', 'json_oauth_profile_section', 50 );
13+
14+
/**
15+
* Register the admin page
16+
*/
17+
function json_oauth_admin_register() {
18+
/**
19+
* Include anything we need that relies on admin classes/functions
20+
*/
21+
include_once dirname( __FILE__ ) . '/lib/class-wp-json-authentication-oauth1-listtable.php';
22+
23+
add_users_page(
24+
// Page title
25+
__( 'Registered OAuth Applications', 'json_oauth' ),
26+
27+
// Menu title
28+
_x( 'Applications', 'menu title', 'json_oauth' ),
29+
30+
// Capability
31+
'list_users',
32+
33+
// Menu slug
34+
'json_oauth',
35+
36+
// Callback
37+
'json_oauth_admin_render'
38+
);
39+
}
40+
41+
function json_oauth_admin_prerender() {
42+
$hook = get_plugin_page_hook( 'json_oauth', 'users.php' );
43+
44+
add_action( 'load-' . $hook, 'json_oauth_admin_load' );
45+
}
46+
47+
function json_oauth_admin_load() {
48+
global $wp_list_table;
49+
50+
$wp_list_table = new WP_JSON_Authentication_OAuth1_ListTable();
51+
52+
$wp_list_table->prepare_items();
53+
}
54+
55+
function json_oauth_admin_render() {
56+
global $wp_list_table;
57+
58+
// ...
59+
?>
60+
<div class="wrap">
61+
<h2>
62+
<?php
63+
esc_html_e( 'Registered OAuth Applications', 'json_oauth' );
64+
if ( current_user_can( 'create_users' ) ): ?>
65+
<a href="user-new.php" class="add-new-h2"><?php echo esc_html_x( 'Add New', 'application', 'json_oauth' ); ?></a>
66+
<?php
67+
endif;
68+
?>
69+
</h2>
70+
71+
<?php $wp_list_table->views(); ?>
72+
73+
<form action="" method="get">
74+
75+
<?php $wp_list_table->search_box( __( 'Search Applications', 'json_oauth' ), 'json_oauth' ); ?>
76+
77+
<?php $wp_list_table->display(); ?>
78+
79+
</form>
80+
81+
<br class="clear" />
82+
83+
</div>
84+
<?php
85+
}
86+
87+
function json_oauth_admin_validate_parameters( $params ) {
88+
$valid = array();
89+
90+
if ( empty( $params['name'] ) ) {
91+
return new WP_Error( 'json_oauth_missing_name', __( 'Consumer name is required' ) );
92+
}
93+
$valid['name'] = wp_filter_post_kses( $params['name'] );
94+
95+
if ( empty( $params['description'] ) ) {
96+
return new WP_Error( 'json_oauth_missing_description', __( 'Consumer description is required' ) );
97+
}
98+
$valid['description'] = wp_filter_post_kses( $params['description'] );
99+
100+
return $valid;
101+
}
102+
103+
/**
104+
* Handle submission of the add page
105+
*
106+
* @return array|null List of errors. Issues a redirect and exits on success.
107+
*/
108+
function json_oauth_admin_handle_edit_submit( $consumer ) {
109+
$messages = array();
110+
if ( empty( $consumer ) ) {
111+
$did_action = 'add';
112+
check_admin_referer( 'json-oauth-add' );
113+
}
114+
else {
115+
$did_action = 'edit';
116+
check_admin_referer( 'json-oauth-edit-' . $consumer->ID );
117+
}
118+
119+
// Check that the parameters are correct first
120+
$params = json_oauth_admin_validate_parameters( wp_unslash( $_POST ) );
121+
if ( is_wp_error( $params ) ) {
122+
$messages[] = $params->get_error_message();
123+
return $messages;
124+
}
125+
126+
if ( empty( $consumer ) ) {
127+
$authenticator = new WP_JSON_Authentication_OAuth1();
128+
129+
// Create the consumer
130+
$data = array(
131+
'name' => $params['name'],
132+
'description' => $params['description'],
133+
);
134+
$consumer = $result = $authenticator->add_consumer( $data );
135+
}
136+
else {
137+
// Update the existing consumer post
138+
$data = array(
139+
'ID' => $consumer->ID,
140+
'post_title' => $params['name'],
141+
'post_content' => $params['description'],
142+
);
143+
$result = wp_update_post( $data, true );
144+
}
145+
146+
if ( is_wp_error( $result ) ) {
147+
$messages[] = $result->get_error_message();
148+
149+
return $messages;
150+
}
151+
152+
// Success, redirect to alias page
153+
$location = add_query_arg(
154+
array(
155+
'action' => 'json-oauth-edit',
156+
'id' => $consumer->ID,
157+
'did_action' => $did_action,
158+
'processed' => 1,
159+
'_wpnonce' => wp_create_nonce( 'json-oauth-edit-' . $id ),
160+
),
161+
network_admin_url( 'admin.php' )
162+
);
163+
wp_safe_redirect( $location );
164+
exit;
165+
}
166+
167+
/**
168+
* Output alias editing page
169+
*/
170+
function json_oauth_admin_edit_page() {
171+
if ( ! current_user_can( 'edit_users' ) )
172+
wp_die( __( 'You do not have permission to access this page.' ) );
173+
174+
// Are we editing?
175+
$consumer = null;
176+
$form_action = admin_url( 'admin.php?action=json-oauth-add' );
177+
if ( ! empty( $_REQUEST['id'] ) ) {
178+
$id = absint( $_REQUEST['id'] );
179+
$consumer = get_post( $id );
180+
if ( is_wp_error( $consumer ) || empty( $consumer ) ) {
181+
wp_die( __( 'Invalid consumer ID.' ) );
182+
}
183+
184+
$form_action = admin_url( 'admin.php?action=json-oauth-edit' );
185+
}
186+
187+
// Handle form submission
188+
$messages = array();
189+
if ( ! empty( $_POST['submit'] ) ) {
190+
$messages = json_oauth_admin_handle_edit_submit( $consumer );
191+
}
192+
193+
$data = array();
194+
195+
if ( empty( $consumer ) || ! empty( $_POST['_wpnonce'] ) ) {
196+
foreach ( array( 'name', 'description' ) as $key ) {
197+
$data[ $key ] = empty( $_POST[ $key ] ) ? '' : wp_unslash( $_POST[ $key ] );
198+
}
199+
}
200+
else {
201+
$data['name'] = $consumer->post_title;
202+
$data['description'] = $consumer->post_content;
203+
}
204+
205+
// Header time!
206+
global $title, $parent_file, $submenu_file;
207+
$title = $consumer ? __( 'Edit Consumer' ) : __( 'Add Consumer' );
208+
$parent_file = 'users.php';
209+
$submenu_file = 'json_oauth';
210+
211+
include( ABSPATH . 'wp-admin/admin-header.php' );
212+
?>
213+
214+
<div class="wrap">
215+
<h2 id="edit-site"><?php echo esc_html( $title ) ?></h2>
216+
217+
<?php
218+
if ( ! empty( $messages ) ) {
219+
foreach ( $messages as $msg )
220+
echo '<div id="message" class="updated"><p>' . $msg . '</p></div>';
221+
}
222+
?>
223+
224+
<form method="post" action="<?php echo esc_url( $form_action ) ?>">
225+
<table class="form-table">
226+
<tr>
227+
<th scope="row">
228+
<label for="oauth-name"><?php echo esc_html_x( 'Consumer Name', 'field name' ) ?></label>
229+
</th>
230+
<td>
231+
<input type="text" class="regular-text"
232+
name="name" id="oauth-name"
233+
value="<?php echo esc_attr( $data['name'] ) ?>" />
234+
</td>
235+
</tr>
236+
<tr>
237+
<th scope="row">
238+
<label for="oauth-description"><?php echo esc_html_x( 'Description', 'field name' ) ?></label>
239+
</th>
240+
<td>
241+
<textarea class="regular-text" name="description" id="oauth-description"
242+
cols="30" rows="5" style="width: 500px"><?php echo esc_textarea( $data['description'] ) ?></textarea>
243+
</td>
244+
</tr>
245+
</table>
246+
247+
<?php
248+
249+
if ( empty( $consumer ) ) {
250+
wp_nonce_field( 'json-oauth-add' );
251+
submit_button( __( 'Add Consumer' ) );
252+
}
253+
else {
254+
echo '<input type="hidden" name="id" value="' . esc_attr( $consumer->ID ) . '" />';
255+
wp_nonce_field( 'json-oauth-edit-' . $consumer->ID );
256+
submit_button( __( 'Save Consumer' ) );
257+
}
258+
259+
?>
260+
</form>
261+
</div>
262+
263+
<?php
264+
265+
include(ABSPATH . 'wp-admin/admin-footer.php');
266+
}
267+
268+
function json_oauth_profile_section( $user ) {
269+
global $wpdb;
270+
271+
$results = $wpdb->get_col( "SELECT option_value FROM {$wpdb->options} WHERE option_name LIKE 'oauth1_access_%'", 0 );
272+
$results = array_map( 'unserialize', $results );
273+
$approved = array_filter( $results, function ( $row ) use ( $user ) {
274+
return $row['user'] === $user->ID;
275+
} );
276+
277+
$authenticator = new WP_JSON_Authentication_OAuth1();
278+
279+
?>
280+
<table class="form-table">
281+
<tbody>
282+
<tr>
283+
<th scope="row"><?php _e( 'Authorized Applications', 'json_oauth' ) ?></th>
284+
<td>
285+
<table class="widefat sessions-table">
286+
<thead>
287+
<tr>
288+
<th scope="col"><?php _e( 'Application Name', 'wpsm' ); ?></th>
289+
</tr>
290+
</thead>
291+
<tbody>
292+
<?php foreach ( $approved as $row ): ?>
293+
<?php
294+
$application = $authenticator->get_consumer( $row['consumer'] );
295+
?>
296+
<tr>
297+
<td><?php echo esc_html( $application->post_title ) ?></td>
298+
<td><button class="button" name="oauth_revoke" value="<?php echo esc_attr( $row['key'] ) ?>"><?php esc_html_e( 'Revoke', 'json_oauth' ) ?></button>
299+
</tr>
300+
301+
<?php endforeach ?>
302+
</tbody>
303+
</table>
304+
</td>
305+
</tr>
306+
</tbody>
307+
</table>
308+
<?php
309+
}
Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
<?php
2+
3+
class WP_JSON_Authentication_OAuth1_ListTable extends WP_List_Table {
4+
public function prepare_items() {
5+
$paged = $this->get_pagenum();
6+
7+
$args = array(
8+
'post_type' => 'json_consumer',
9+
'post_status' => 'any',
10+
'meta_query' => array(
11+
array(
12+
'key' => 'type',
13+
'value' => 'oauth1',
14+
),
15+
),
16+
17+
'paged' => $paged,
18+
);
19+
20+
$query = new WP_Query();
21+
$this->items = $query->query( $args );
22+
}
23+
24+
/**
25+
* Get a list of columns for the list table.
26+
*
27+
* @since 3.1.0
28+
* @access public
29+
*
30+
* @return array Array in which the key is the ID of the column,
31+
* and the value is the description.
32+
*/
33+
public function get_columns() {
34+
$c = array(
35+
'cb' => '<input type="checkbox" />',
36+
'name' => __( 'Name' ),
37+
'description' => __( 'Description' ),
38+
);
39+
40+
return $c;
41+
}
42+
43+
public function column_cb( $item ) {
44+
?>
45+
<label class="screen-reader-text" for="cb-select-<?php echo $item->ID ?>"><?php _e( 'Select consumer' ); ?></label>
46+
<input id="cb-select-<?php echo $item->ID ?>" type="checkbox" name="consumers[]" value="<?php echo $item->ID ?>" />
47+
<?php
48+
}
49+
50+
protected function column_name( $item ) {
51+
$title = get_the_title( $item->ID );
52+
if ( empty( $title ) ) {
53+
$title = '<em>' . __( 'Untitled' ) . '</em>';
54+
}
55+
56+
$edit_link = add_query_arg(
57+
array(
58+
'action' => 'json-oauth-edit',
59+
'id' => $item->ID,
60+
),
61+
admin_url( 'admin.php' )
62+
);
63+
64+
$actions = array(
65+
'edit' => sprintf( '<a href="%s">%s</a>', $edit_link, __( 'Edit' ) ),
66+
);
67+
$action_html = $this->row_actions( $actions );
68+
69+
return $title . ' ' . $action_html;
70+
}
71+
72+
protected function column_description( $item ) {
73+
return $item->post_content;
74+
}
75+
}

oauth-server.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@
88
include_once( dirname( __FILE__ ) . '/lib/class-wp-json-authentication-oauth1.php' );
99
include_once( dirname( __FILE__ ) . '/lib/class-wp-json-authentication-oauth1-authorize.php' );
1010

11+
include_once( dirname( __FILE__ ) . '/admin.php' );
12+
1113
if ( defined( 'WP_CLI' ) && WP_CLI ) {
1214
include_once( dirname( __FILE__ ) . '/lib/class-wp-json-authentication-oauth1-cli.php' );
1315

0 commit comments

Comments
 (0)