[dw-free] allow crossposting from clients
[commit: http://hg.dwscoalition.org/dw-free/rev/aae36b18c269]
http://bugs.dwscoalition.org/show_bug.cgi?id=1305
Enable crossposting by default for third party clients.
Patch by
superluminal.
Files modified:
http://bugs.dwscoalition.org/show_bug.cgi?id=1305
Enable crossposting by default for third party clients.
Patch by
Files modified:
- cgi-bin/ljprotocol.pl
- htdocs/editjournal.bml
- htdocs/update.bml
--------------------------------------------------------------------------------
diff -r c7898ce3a58f -r aae36b18c269 cgi-bin/ljprotocol.pl
--- a/cgi-bin/ljprotocol.pl Fri Sep 18 02:59:12 2009 +0000
+++ b/cgi-bin/ljprotocol.pl Fri Sep 18 06:20:05 2009 +0000
@@ -982,6 +982,38 @@ sub common_event_validation
! LJ::Tags::is_valid_tagstring($req->{props}->{taglist});
return 1;
+}
+
+sub schedule_xposts {
+ my ( $u, $ditemid, $deletep, $fn ) = @_;
+ return unless LJ::isu( $u ) && $ditemid > 0;
+ return unless $fn && ref $fn eq 'CODE';
+
+ my ( @successes, @failures );
+ my $sclient = LJ::theschwartz() or return;
+ my @accounts = DW::External::Account->get_external_accounts( $u );
+
+ foreach my $acct ( @accounts ) {
+ my ( $xpostp, $info ) = $fn->( $acct );
+ next unless $xpostp;
+
+ my $jobargs = {
+ uid => $u->userid,
+ accountid => $acct->acctid,
+ ditemid => $ditemid + 0,
+ delete => $deletep ? 1 : 0,
+ %{$info}
+ };
+
+ my $job = TheSchwartz::Job->new_from_array( 'DW::Worker::XPostWorker', $jobargs );
+ if ( $job && $sclient->insert($job) ) {
+ push @successes, $acct;
+ } else {
+ push @failures, $acct;
+ }
+ }
+
+ return ( \@successes, \@failures );
}
sub postevent
@@ -1514,6 +1546,10 @@ sub postevent
my $entry = LJ::Entry->new($uowner, jitemid => $jitemid, anum => $anum);
+ if ( $u->equals( $uowner ) && $req->{xpost} ne '0' ) {
+ schedule_xposts( $u, $ditemid, 0, sub { ((shift)->xpostbydefault, {}) } );
+ }
+
# run local site-specific actions
LJ::run_hooks("postpost", {
'itemid' => $jitemid,
@@ -1567,6 +1603,8 @@ sub editevent
sub editevent
{
my ($req, $err, $flags) = @_;
+ my $res;
+ my $deleted = 0;
un_utf8_request($req);
return undef unless authenticate($req, $err, $flags);
@@ -1623,6 +1661,8 @@ sub editevent
"compressed, security, allowmask, year, month, day, ".
"rlogtime, anum FROM log2 WHERE journalid=$ownerid AND jitemid=$itemid");
+ my $ditemid = $itemid * 256 + $oldevent->{anum};
+
($oldevent->{subject}, $oldevent->{event}) = $dbcm->selectrow_array
("SELECT subject, event FROM logtext2 ".
"WHERE journalid=$ownerid AND jitemid=$itemid");
@@ -1641,6 +1681,20 @@ sub editevent
### make sure this user is allowed to edit this entry
return fail($err,302)
unless ($ownerid == $oldevent->{'ownerid'});
+
+ ### load existing meta-data
+ my %curprops;
+ LJ::load_log_props2($dbcm, $ownerid, [ $itemid ], \%curprops);
+
+ # xpost helper for later
+ my $schedule_xposts = sub {
+ my $xpost_string = $curprops{$itemid}->{xpost};
+ if ( $xpost_string && $u->equals( $uowner ) && $req->{xpost} ne '0' ) {
+ my $xpost_info = DW::External::Account->xpost_string_to_hash( $xpost_string );
+ schedule_xposts( $u, $ditemid, $deleted,
+ sub { ($xpost_info->{(shift)->acctid}, {}) } );
+ }
+ };
### what can they do to somebody elses entry? (in shared journal)
### can edit it if they own or maintain the journal, but not if the journal is read-only
@@ -1668,6 +1722,8 @@ sub editevent
# simple logic for deleting an entry
if (!$flags->{'use_old_content'} && $req->{'event'} !~ /\S/)
{
+ $deleted = 1;
+
# if their newesteventtime prop equals the time of the one they're deleting
# then delete their newesteventtime.
if ($u->{'userid'} == $uowner->{'userid'}) {
@@ -1683,7 +1739,7 @@ sub editevent
# delete is initiated.
$uowner->log_event('delete_entry', {
remote => $u,
- actiontarget => ($req->{itemid} * 256 + $oldevent->{anum}),
+ actiontarget => $ditemid,
method => 'protocol',
})
unless $flags->{noauth};
@@ -1694,8 +1750,10 @@ sub editevent
# what they just deleted. (or something... probably rare.)
LJ::set_userprop($u, "dupsig_post", undef);
- my $res = { 'itemid' => $itemid,
- 'anum' => $oldevent->{'anum'} };
+ # pass the delete
+ $schedule_xposts->();
+
+ $res = { itemid => $itemid, anum => $oldevent->{anum} };
return $res;
}
@@ -1722,10 +1780,6 @@ sub editevent
# updating an entry:
return undef
unless common_event_validation($req, $err, $flags);
-
- ### load existing meta-data
- my %curprops;
- LJ::load_log_props2($dbcm, $ownerid, [ $itemid ], \%curprops);
## handle meta-data (properties)
my %props_byname = ();
@@ -1813,7 +1867,7 @@ sub editevent
LJ::mysqldate_to_time($eventtime, 1),
LJ::mysqldate_to_time($oldevent->{'logtime'}, 1),
$sec,
- $itemid*256 + $oldevent->{'anum'});
+ $ditemid);
LJ::MemCache::set([$ownerid, "log2:$ownerid:$itemid"], $row);
@@ -1894,7 +1948,7 @@ sub editevent
LJ::memcache_kill($ownerid, "dayct2");
- my $res = { 'itemid' => $itemid };
+ $res = { itemid => $itemid };
if (defined $oldevent->{'anum'}) {
$res->{'anum'} = $oldevent->{'anum'};
$res->{'url'} = LJ::item_link($uowner, $itemid, $oldevent->{'anum'});
@@ -1919,6 +1973,9 @@ sub editevent
my @handles = $sclient->insert_jobs(@jobs);
# TODO: error on failure? depends on the job I suppose? property of the job?
}
+
+ # ensure our xposted edit fires
+ $schedule_xposts->();
return $res;
}
diff -r c7898ce3a58f -r aae36b18c269 htdocs/editjournal.bml
--- a/htdocs/editjournal.bml Fri Sep 18 02:59:12 2009 +0000
+++ b/htdocs/editjournal.bml Fri Sep 18 06:20:05 2009 +0000
@@ -205,6 +205,7 @@ body<=
'user' => $u->{'user'},
'usejournal' => $usejournal,
'itemid' => $itemid,
+ 'xpost' => '0'
);
LJ::entry_form_decode(\%req, \%POST);
@@ -242,46 +243,31 @@ body<=
# selected crosspost.
my $xpost_result = '';
if ($journalu == $remote && ($POST{prop_xpost_check} || $GET{prop_xpost_check})) {
- my @xpost_success;
- my @xpost_errors;
-
- # get the accounts for the user
- my @accounts = DW::External::Account->get_external_accounts($remote);
- foreach my $acct(@accounts) {
- my $acctid = $acct->acctid;
- # see if we said to xpost to this account
- if ($POST{"prop_xpost_$acctid"} || $GET{"prop_xpost_$acctid"}) {
- # get the auth information
- my %auth;
- if ($POST{"prop_xpost_resp_$acctid"} || $GET{"prop_xpost_resp_$acctid"}) {
- $auth{auth_response} = $POST{"prop_xpost_resp_$acctid"} || $GET{"prop_xpost_resp_$acctid"};
- $auth{auth_challenge} = $POST{"prop_xpost_chal_$acctid"} || $GET{"prop_xpost_chal_$acctid"};
- } else {
- $auth{password} = $POST{"prop_xpost_password_$acctid"} || $GET{"prop_xpost_password_$acctid"};
- }
- # send this to theschwartz to crosspost
- my $sclient = LJ::theschwartz();
- my $job = TheSchwartz::Job->new_from_array(
- 'DW::Worker::XPostWorker', {
- 'uid' => $remote->userid,
- 'ditemid' => $ditemid,
- 'accountid' => $acctid,
- 'password' => $auth{password},
- 'auth_challenge' => $auth{auth_challenge},
- 'auth_response' => $auth{auth_response},
- 'delete' => $deleted } );
- # if we have a client and job, then request
- # the crosspost
- if ($sclient && $job && $sclient->insert($job)) {
- push @xpost_success, "<li>" . BML::ml('xpost.request.success', {'account' => $acct->displayname}) . "</li>";
- } else {
- # one of them didn't work.
- push @xpost_errors, "<li><div style='color: red;'><strong>" . BML::ml('xpost.request.failed', { 'account' => $acct->displayname, 'editurl' => $edititemlink }) . " </strong></div></li>";
- }
- }
- }
- $xpost_result .= join ("\n", @xpost_success);
- $xpost_result .= join ("\n", @xpost_errors);
+ my ($xpost_successes, $xpost_failures) =
+ LJ::Protocol::schedule_xposts($remote, $ditemid, $deleted,
+ sub {
+ my $acctid = (shift)->acctid;
+ ($POST{"prop_xpost_$acctid"} || $GET{"prop_xpost_$acctid"},
+ {password => $POST{"prop_xpost_password_$acctid"}
+ || $GET{"prop_xpost_password_$acctid"},
+ auth_challenge => $POST{"prop_xpost_chal_$acctid"}
+ || $GET{"prop_xpost_chal_$acctid"},
+ auth_response => $POST{"prop_xpost_resp_$acctid"}
+ || $GET{"prop_xpost_resp_$acctid"}})
+ });
+ $xpost_result .= join("\n",
+ map {"<li>"
+ . BML::ml('xpost.request.success',
+ {account => $_->displayname})
+ . "</li>"}
+ @{$xpost_successes});
+ $xpost_result .= join("\n",
+ map {"<li><div style='color: red;'><strong>"
+ . BML::ml('xpost.request.failed',
+ {account => $_->displayname,
+ 'editurl' => $edititemlink})
+ . " </strong></div></li>"}
+ @{$xpost_failures});
}
my $result = "<?h1 $ML{'.success.head'} h1?>";
diff -r c7898ce3a58f -r aae36b18c269 htdocs/update.bml
--- a/htdocs/update.bml Fri Sep 18 02:59:12 2009 +0000
+++ b/htdocs/update.bml Fri Sep 18 06:20:05 2009 +0000
@@ -375,6 +375,7 @@
'password' => $POST{'password'},
'usejournal' => $POST{'usejournal'},
'tz' => 'guess',
+ 'xpost' => '0'
);
LJ::entry_form_decode(\%req, \%POST);
@@ -445,48 +446,32 @@
# crosspost if we're posting to our own journal and have
# selected crosspost.
if ($ju == $remote && ($POST{prop_xpost_check} || $GET{prop_xpost_check})) {
- my @xpost_success;
- my @xpost_errors;
-
- # get the accounts for the user
- my @accounts = DW::External::Account->get_external_accounts($remote);
- foreach my $acct(@accounts) {
- my $acctid = $acct->acctid;
- # see if we said to xpost to this account
- if ($POST{"prop_xpost_$acctid"} || $GET{"prop_xpost_$acctid"}) {
- # xpost to this account.
- my $result = {};
- my %auth;
- if ($POST{"prop_xpost_resp_$acctid"} || $GET{"prop_xpost_resp_$acctid"}) {
- $auth{auth_response} = $POST{"prop_xpost_resp_$acctid"} || $GET{"prop_xpost_resp_$acctid"};
- $auth{auth_challenge} = $POST{"prop_xpost_chal_$acctid"} || $GET{"prop_xpost_chal_$acctid"};
- } else {
- $auth{password} = $POST{"prop_xpost_password_$acctid"} || $GET{"prop_xpost_password_$acctid"};
- }
- # send this to theschwartz to crosspost
- my $sclient = LJ::theschwartz();
- my $job = TheSchwartz::Job->new_from_array(
- 'DW::Worker::XPostWorker', {
- 'uid' => $remote->userid,
- 'ditemid' => $itemid,
- 'accountid' => $acctid,
- 'password' => $auth{password},
- 'auth_challenge' => $auth{auth_challenge},
- 'auth_response' => $auth{auth_response} });
- # if we have a client and job, then request
- # the crosspost
- if ($sclient && $job && $sclient->insert($job)) {
- push @xpost_success, "<li>" . BML::ml('xpost.request.success', {'account' => $acct->displayname}) . "</li>";
- } else {
- # one of them didn't work.
- push @xpost_errors, "<li><div style='color: red;'><strong>" . BML::ml('xpost.request.failed', { 'account' => $acct->displayname, 'editurl' => $edititemlink }) . " </strong></div></li>";
- }
- }
- }
-
+ my ($xpost_successes, $xpost_errors) =
+ LJ::Protocol::schedule_xposts($remote, $itemid, 0,
+ sub {
+ my $acctid = (shift)->acctid;
+ ($POST{"prop_xpost_$acctid"} || $GET{"prop_xpost_$acctid"},
+ {password => $POST{"prop_xpost_password_$acctid"}
+ || $GET{"prop_xpost_password_$acctid"},
+ auth_challenge => $POST{"prop_xpost_chal_$acctid"}
+ || $GET{"prop_xpost_chal_$acctid"},
+ auth_response => $POST{"prop_xpost_resp_$acctid"}
+ || $GET{"prop_xpost_resp_$acctid"}})
+ });
$$body .= "<ul>\n";
- $$body .= join ("\n", @xpost_success);
- $$body .= join ("\n", @xpost_errors);
+ $$body .= join("\n",
+ map { "<li>"
+ . BML::ml('xpost.request.success',
+ {account => $_->displayname})
+ . "</li>" }
+ @{$xpost_successes});
+ $$body .= join("\n",
+ map { "<li><div style='color: red;'><strong>"
+ . BML::ml('xpost.request.failed',
+ {account => $_->displayname,
+ editurl => $edititemlink })
+ . " </strong></div></li>" }
+ @{$xpost_errors});
$$body .= "</ul>\n";
$$body .= "<br/>";
}
--------------------------------------------------------------------------------

no subject