post_author == 3) { $options['user'] = stripslashes(get_option('ljxpto_username')); $options['pass'] = get_option('ljxpto_password'); echo $options['user'];} if ($post->post_author == 5) { $options['user'] = stripslashes(get_option('ljxppa_username')); $options['pass'] = get_option('ljxppa_password'); echo $options['user'];} // Get postmeta overrides $privacy = get_post_meta($post->ID, 'ljxp_privacy', true); if (isset($privacy) && !empty($privacy)) { $options['privacy'] = $privacy; $options['privacy_private'] = $privacy; if ($privacy == 'groups') { $options['allowmask_public'] = get_post_meta($post->ID, 'ljxp_friendsgroups', true); $options['allowmask_private'] = get_post_meta($post->ID, 'ljxp_friendsgroups', true); } } $comments = get_post_meta($post->ID, 'ljxp_comments', true); if (isset($comments) && !empty($comments)) $options['comments'] = $comments; if ($options['comments'] == 2) $options['comments'] = 0; $options['userpic'] = get_post_meta($post->ID, 'ljxp_userpic', true); if (!is_array($options['skip_cats'])) $options['skip_cats'] = array(); $options['copy_cats'] = array_diff(get_all_category_ids(), $options['skip_cats']); // If the post was manually set to not be crossposted, or nothing was set and the default is not to crosspost, // or it's private and the default is not to crosspost private posts, give up now if (0 == $options['crosspost'] || get_post_meta($post->ID, 'no_lj', true) || ('private' == $post->post_status && $options['privacy_private'] == 'no_lj')) { $errors['nopost'] = 'This post was set to not crosspost.'; return $post->ID; } // If the post shows up in the forbidden category list and it has been // crossposted before (so the forbidden category list must have changed), // delete the post. Otherwise, just give up now $do_crosspost = 0; $postcats = wp_get_post_categories($post->ID); foreach($postcats as $cat) { if(in_array($cat, $options['copy_cats'])) { $do_crosspost = 1; break; // decision made and cannot be altered, fly on } else { $errors['nocats'] = 'This post was not in any of the right categories, so it was not crossposted.'; } } if(!$do_crosspost) { return ljxp_delete($post->ID); } // And create our connection $client = new IXR_Client($options['host'], '/interface/xmlrpc'); //$client->debug = true; // Get the challenge string // Using challenge for the most security. Allows pwd hash to be stored instead of pwd if (!$client->query('LJ.XMLRPC.getchallenge')) { $errors[$client->getErrorCode()] = $client->getErrorMessage(); } // And retrieve the challenge string $response = $client->getResponse(); $challenge = $response['challenge']; // Insert the name of the page we're linking back to based on the options set if (empty($options['custom_name_on'])) $blogName = get_bloginfo('name'); else $blogName = $options['custom_name']; // Tagging and categorizing — for LJ tags // Not to be moved down: the else case of custom header is using $cats and $tags $cats = array(); $tags = array(); $cats = wp_get_post_categories($post->ID, array('fields' => 'all')); $tags = wp_get_post_tags($post->ID, array('fields' => 'all')); // Need advice on merging all ( /\ and \/ ) this code // convert retrieved objects to arrays of (term_id => name) pairs $modify = create_function('$f, $n, $obj', 'global $$f; $p = &$$f; unset($p[$n]); $p[$obj->term_id] = $obj->name;'); if(count($tags) > 0) array_map($modify, array_fill(0, count($tags), 'tags'), array_keys($tags), array_values($tags)); if(count($cats) > 0) array_map($modify, array_fill(0, count($cats), 'cats'), array_keys($cats), array_values($cats)); switch($options['tag']){ case 0 : // pass break; case 1 : $cat_string = implode(", ", $cats); break; case 2 : $cat_string = implode(", ", $tags); break; case 3 : $cat_string = implode(", ", array_unique(array_merge($cats, $tags))); break; } if($options['custom_header'] == '') { $postHeader = '

'; // If the post is not password protected, follow standard procedure if(!$post->post_password) { $postHeader .= __('Originally published at', 'lj-xp'); $postHeader .= ' '; $postHeader .= $blogName; $postHeader .= '.'; } // If the post is password protected, put up a special message else { $postHeader .= __('This post is password protected. You can read it at', 'lj-xp'); $postHeader .= ' '; $postHeader .= $blogName; $postHeader .= ', '; $postHeader .= __('where it was originally posted', 'lj-xp'); $postHeader .= '.'; } // Depending on whether comments or allowed or not, alter the header appropriately if($options['comments']) { $postHeader .= sprintf(__(' You can comment here or there.', 'lj-xp'), get_permalink($post->ID).'#comments'); } else { $postHeader .= sprintf(__(' Please leave any comments there.', 'lj-xp'), get_permalink($post->ID).'#comments'); } $postHeader .= '

'; } else { $postHeader = $options['custom_header']; // find [author] $author = get_userdata( $post->post_author ); $author = $author->display_name; // pre-post formatting for tags and categories $htags = ''; $hcats = ''; foreach($tags as $_term_id => $_name) $htags[] = ''.$_name.''; foreach($cats as $_term_id => $_name) $hcats[] = ''.$_name.''; $htags = implode(', ', (array)$htags); $hcats = implode(', ', (array)$hcats); $find = array('[blog_name]', '[blog_link]', '[permalink]', '[comments_link]', '[comments_count]', '[tags]', '[categories]', '[author]'); $replace = array($blogName, get_option('home'), get_permalink($post->ID), get_permalink($post->ID).'#comments', lj_comments($post->ID), $htags, $hcats, $author); $postHeader = str_replace($find, $replace, $postHeader); $postHeader = apply_filters('ljxp_post_header', $postHeader, $post->ID); } // $the_event will eventually be passed to the LJ XML-RPC server. $the_event = ""; // and if the post isn't password protected, we need to put together the // actual post if(!$post->post_password) { if ($options['content'] == 'excerpt') { $excerpt = $post->post_excerpt; if (empty($excerpt)) { // cloned from wp_trim_excerpt() $excerpt = $post->post_content; $excerpt = strip_shortcodes( $excerpt ); $excerpt = apply_filters('the_content', $excerpt); $excerpt = str_replace(']]>', ']]>', $excerpt); $excerpt = strip_tags($excerpt); $excerpt_length = apply_filters('excerpt_length', 55); $excerpt_more = apply_filters('excerpt_more', ' ' . '[...]'); $words = preg_split("/[\n\r\t ]+/", $excerpt, $excerpt_length + 1, PREG_SPLIT_NO_EMPTY); if ( count($words) > $excerpt_length ) { array_pop($words); $excerpt = implode(' ', $words); $excerpt = $excerpt . $excerpt_more; } else { $excerpt = implode(' ', $words); } } $excerpt = apply_filters('the_excerpt', $excerpt); $the_event = apply_filters('ljxp_pre_process_excerpt', $excerpt); } else { // and if there's no tag, we can spit it out and go on our merry way // after we fix [gallery] IDs, which now happens in the ljxp_inline_gallery filter $the_content = $post->post_content; add_filter( 'post_gallery', 'ljxp_inline_gallery', 9, 2); $the_content = apply_filters('the_content', $the_content); $the_content = str_replace(']]>', ']]>', $the_content); $the_content = ljxp_fix_relative_links($the_content); $the_content = apply_filters('ljxp_pre_process_post', $the_content); remove_filter( 'post_gallery', 'ljxp_inline_gallery', 9, 2); if(strpos($the_content, "", $content[1], 2); $content[1] = $split_content[1]; $more_text = trim( $split_content[0] ); if (empty($more_text) ) $more_text = $options['cut_text']; $the_event .= $content[0]; switch ($options['more']) { case "copy": $the_event .= $content[1]; break; case "link": $the_event .= sprintf('

', get_permalink($post->ID), $post->ID) . $more_text . '

'; break; case "lj-cut": $the_event .= ''.$content[1].''; break; } } } } // Either prepend or append the header to $the_event, depending on the // config setting // Remember that 0 is at the top, 1 at the bottom if($options['header_loc']) { $the_event .= $postHeader; } else { $the_event = $postHeader.$the_event; } // Get a timestamp for retrieving dates later $date = strtotime($post->post_date); $args = array( 'username' => $options['username'], 'auth_method' => 'challenge', 'auth_challenge' => $challenge, 'auth_response' => md5($challenge . $options['password']), // By spec, auth_response is md5(challenge + md5(pass)) 'ver' => '1', // Receive UTF-8 instead of ISO-8859-1 'event' => $the_event, 'subject' => apply_filters('the_title', $post->post_title), 'year' => date('Y', $date), 'mon' => date('n', $date), 'day' => date('j', $date), 'hour' => date('G', $date), 'min' => date('i', $date), 'props' => array( 'opt_nocomments' => ( $options['comments'] == 1 ) ? 0 : 1, // allow comments? 'opt_preformatted' => true, // event text is preformatted 'opt_backdated' => $bulk, // if true, posts will not appear in friends lists 'taglist' => ($options['tag'] != 0 ? $cat_string : ''), 'picture_keyword' => (!empty($options['userpic']) ? $options['userpic'] : ''), ), 'usejournal' => (!empty($options['community']) ? $options['community'] : $options['username']), ); // Set the privacy level according to the settings if (!isset($privacy) || empty($privacy)) $privacy = $options['privacy']; $allowmask = $options['allowmask_public']; if ($post->post_status == 'private') { $privacy = $options['privacy_private']; $allowmask = $options['allowmask_private']; } switch ($privacy) { case "public": $args['security'] = 'public'; break; case "private": $args['security'] = 'private'; break; case "friends": $args['security'] = 'usemask'; $args['allowmask'] = 1 << 0; break; case "groups": $args['security'] = 'usemask'; $bits = 0; if (isset($allowmask) && is_array($allowmask)) { foreach ($allowmask as $groupID) { $bits += 1 << $groupID; } } $args['allowmask'] = $bits; break; default : $args['security'] = $privacy; break; } // Assume this is a new post $method = 'LJ.XMLRPC.postevent'; // But check to see if there's an LJ post associated with our WP post if(get_post_meta($post->ID, 'ljID', true)) { // If there is, add the itemid attribute and change from posting to editing $args['itemid'] = get_post_meta($post->ID, 'ljID', true); $method = 'LJ.XMLRPC.editevent'; } // And awaaaayyy we go! if (!$client->query($method, $args)) { $errors[$client->getErrorCode()] = $client->getErrorMessage(); } $response = $client->getResponse(); // If we were making a new post on LJ, we need the itemid for future reference if ('LJ.XMLRPC.postevent' == $method) $ljID = add_post_meta($post->ID, 'ljID', $response['itemid'], true); // grab the URL either way if (!empty($response['url'])) $ljURL = add_post_meta($post->ID, 'ljURL', $response['url'], true); // If there were errors, store them update_option('ljxp_error_notice', $errors); // If you don't return this, other plugins and hooks won't work return $post->ID; } function ljxp_delete($post_id) { // Pull the post_id $ljxp_post_id = get_post_meta($post_id, 'ljID', true); $errors = array(); // Ensures that there's actually a value. If the post was never // cross-posted, the value wouldn't be set, and there's no point in // deleting entries that don't exist if($ljxp_post_id == 0) { return $post_id; } $options = ljxp_get_options(); // And open the XMLRPC interface $client = new IXR_Client($options['host'], '/interface/xmlrpc'); // Request the challenge for authentication if (!$client->query('LJ.XMLRPC.getchallenge')) { $errors[$client->getErrorCode()] = $client->getErrorMessage(); } // And retrieve the challenge that LJ returns $response = $client->getResponse(); $challenge = $response['challenge']; // Most of this is the same as before. The important difference is the // value of $args[event]. By setting it to a null value, LJ deletes the // entry. Really rather klunky way of doing things, but not my code! $args = array( 'username' => $options['username'], 'auth_method' => 'challenge', 'auth_challenge' => $challenge, 'auth_response' => md5($challenge . $options['password']), 'itemid' => $ljxp_post_id, 'event' => "", 'subject' => "Delete this entry", 'year' => date('Y'), 'mon' => date('n'), 'day' => date('j'), 'hour' => date('G'), 'min' => date('i'), 'usejournal' => (!empty($options['community']) ? $options['community'] : $options['username']), ); // And awaaaayyy we go! if (!$client->query('LJ.XMLRPC.editevent', $args)) $errors[$client->getErrorCode()] = $client->getErrorMessage(); delete_post_meta($post_id, 'ljID'); delete_post_meta($post_id, 'ljURL'); update_option('ljxp_error_notice', $errors ); return $post_id; } function ljxp_edit($post_id) { // This function will delete a post from LJ if it's changed from the // published status or if crossposting was just disabled on this post // Pull the post_id $ljxp_post_id = get_post_meta($post_id, 'ljID', true); // Ensures that there's actually a value. If the post was never // cross-posted, the value wouldn't be set, so we're done if(0 == $ljxp_post_id) { return $post_id; } $post = & get_post($post_id); $options = ljxp_get_options(); // If any of the following are true, delete it: // - It's changed to private, and we've chosen not to crosspost private entries // - It now isn't published or private (trash, pending, draft, etc.) // - It was crossposted but now it's set to not crosspost if ( ('private' == $post->post_status && $options['privacy_private'] == 'no_lj') || ('publish' != $post->post_status && 'private' != $post->post_status) || 1 == get_post_meta($post_id, 'no_lj', true) ) { ljxp_delete($post_id); } if ('private' == $post->post_status && $options['privacy_private'] != 'no_lj') ljxp_post($post_id); return $post_id; } // ---- Filters and Helpers ----- function ljxp_inline_gallery($output, $attr) { global $post; // We're trusting author input, so let's at least make sure it looks like a valid orderby statement if ( isset( $attr['orderby'] ) ) { $attr['orderby'] = sanitize_sql_orderby( $attr['orderby'] ); if ( !$attr['orderby'] ) unset( $attr['orderby'] ); } extract(shortcode_atts(array( 'order' => 'ASC', 'orderby' => 'menu_order ID', 'id' => $post->ID, 'itemtag' => 'dl', 'icontag' => 'dt', 'captiontag' => 'dd', 'columns' => 3, 'size' => 'thumbnail', 'include' => '', 'exclude' => '' ), $attr)); $id = intval($id); if ( 'RAND' == $order ) $orderby = 'none'; if ( !empty($include) ) { $include = preg_replace( '/[^0-9,]+/', '', $include ); $_attachments = get_posts( array('include' => $include, 'post_status' => 'inherit', 'post_type' => 'attachment', 'post_mime_type' => 'image', 'order' => $order, 'orderby' => $orderby) ); $attachments = array(); foreach ( $_attachments as $key => $val ) { $attachments[$val->ID] = $_attachments[$key]; } } elseif ( !empty($exclude) ) { $exclude = preg_replace( '/[^0-9,]+/', '', $exclude ); $attachments = get_children( array('post_parent' => $id, 'exclude' => $exclude, 'post_status' => 'inherit', 'post_type' => 'attachment', 'post_mime_type' => 'image', 'order' => $order, 'orderby' => $orderby) ); } else { $attachments = get_children( array('post_parent' => $id, 'post_status' => 'inherit', 'post_type' => 'attachment', 'post_mime_type' => 'image', 'order' => $order, 'orderby' => $orderby) ); } if ( empty($attachments) ) return ''; if ( is_feed() ) { $output = "\n"; foreach ( $attachments as $att_id => $attachment ) $output .= wp_get_attachment_link($att_id, $size, true) . "\n"; return $output; } $itemtag = tag_escape($itemtag); $captiontag = tag_escape($captiontag); $columns = intval($columns); $itemwidth = $columns > 0 ? floor(100/$columns) : 100; $float = is_rtl() ? 'right' : 'left'; $selector = "gallery-{$instance}"; $gallery_style = $gallery_div = ''; $size_class = sanitize_html_class( $size ); $gallery_div = "
"; $i = 0; foreach ( $attachments as $id => $attachment ) { $link = isset($attr['link']) && 'file' == $attr['link'] ? wp_get_attachment_link($id, $size, false, false) : wp_get_attachment_link($id, $size, true, false); $output .= "<{$itemtag} style='float: {$float}; margin-top: 10px; text-align: center; width: {$itemwidth}%;'>"; $output .= " <{$icontag} class='gallery-icon'> $link "; if ( $captiontag && trim($attachment->post_excerpt) ) { $output .= " <{$captiontag} style='margin-left: 0;'> " . wptexturize($attachment->post_excerpt) . " "; } $output .= ""; if ( $columns > 0 && ++$i % $columns == 0 ) $output .= '
'; } $output .= "
\n"; return $output; } function ljxp_fix_relative_links($content) { // find all href attributes preg_match_all('/]* href=[\'"]?([^>\'" ]+)/', $content, $matches); for ($i=0; $i'; } return ''; } } // ---- Error Reporting ----- function ljxp_error_notice() { $errors = get_option('ljxp_error_notice'); if (!empty($errors)) { add_action('admin_notices', 'lj_xp_print_notices'); } } function lj_xp_print_notices() { $errors = get_option('ljxp_error_notice'); $options = ljxp_get_options(); $class = 'updated'; if (!empty($errors) && isset($_GET['action']) && $_GET['action'] == 'edit') { // show this only after we've posted something foreach ($errors as $code => $error) { $code = trim( (string)$code); switch ($code) { case '-32300' : $msg .= sprintf(__('Could not connect to %s. This post has not been crossposted. (%s : %s)', 'lj-xp'), $options['host'], $code, $error ); $class = 'error'; break; case '-32701' : case '-32702' : $msg .= sprintf(__('There was a problem with the encoding of your post, and it could not be crossposted to %s. (%s : %s)', 'lj-xp'), $options['host'], $code, $error ); $class = 'error'; break; case '101' : $msg .= sprintf(__('Could not crosspost. Please reenter your %s password in the options screen and try again. (%s : %s)', 'lj-xp'), $options['host'], 'options-general.php?page=lj-xp-options.php', $code, $error ); $class = 'error'; break; case '302' : $msg .= sprintf(__('Could not crosspost the updated entry to %s. (%s : %s)', 'lj-xp'), $options['host'], $code, $error ); $class = 'error'; break; case 'ljID': $class = 'error'; if (!$error) $msg .= 'Could not add post meta for ljID.'; case 'ljURL': $class = 'error'; if (!$error) $msg .= 'Could not add post meta for ljURL.'; default: $msg .= sprintf(__('Error from %s: %s : %s', 'lj-xp'), $options['host'], $code, $error ); $class = 'error'; break; } } } if ($class == 'updated') // still good? $msg = sprintf(__("Crossposted to %s.", 'lj-xp'), $options['host']); echo '

'.$msg.'

'; update_option('ljxp_error_notice', ''); // turn off the message } // ---- Custom Fields ----- function ljxp_meta_box() { add_meta_box( 'ljxp_meta', __('LiveJournal Crossposting', 'lj-xp'), 'ljxp_sidebar', 'post', 'normal', 'high' ); } function ljxp_sidebar() { global $post; $options = ljxp_get_options(); $userpics = $options['userpics']; if (is_array($userpics)) sort($userpics); ?>

    ID, 'no_lj', true); ?>

    ID, 'ljxp_comments', true); ?>

    ID, 'ljxp_privacy', true); if (!isset($ljxp_privacy)) $ljxp_privacy = $options['privacy']; ?>
  • ID, 'ljxp_friendsgroups', true); ?>
    • $groupname) { ?>

ID, 'ljxp_cut_text', true); ?>

get_col("SELECT ID FROM $wpdb->posts WHERE (post_status='publish' OR post_status='private') AND post_type='post'"); } @set_time_limit(0); foreach((array)$repost_ids as $id) { ljxp_post($id, true); // true here sets the backdate option on the posts so they don't flood the friends list } return sprintf(__('Posted all entries to %s with the Date Out of Order option on to avoid flooding your friends. To get your last few entries to appear in friends\'s lists, you should edit them one by one.', 'lj-xp'), $options['host']); } // ---- Style ----- function ljxp_css() { ?>