353 lines
12 KiB
Plaintext
Executable File
353 lines
12 KiB
Plaintext
Executable File
<?page
|
|
body<=
|
|
<?_code
|
|
{
|
|
use strict;
|
|
use vars qw($head %FORM %ML);
|
|
|
|
$head = ""; # not local, used to build <link> tags
|
|
|
|
return LJ::server_down_html() if $LJ::SERVER_DOWN;
|
|
|
|
my $errtxt;
|
|
|
|
my $pics = LJ::Talk::get_subjecticons();
|
|
|
|
my $r = Apache->request;
|
|
$r->notes("codepath" => "bml.talkpost");
|
|
|
|
my $uri = BML::get_uri();
|
|
|
|
if ($uri =~ m!/(\d+)\.html$!) {
|
|
$FORM{'itemid'} = $1 unless $FORM{'replyto'} > 0;
|
|
$FORM{'journal'} = $r->notes("_journal");
|
|
BML::set_language_scope("/talkpost.bml");
|
|
}
|
|
|
|
my $init = LJ::Talk::init(\%FORM);
|
|
return "<?h1 $ML{'Error'} h1?><?p $init->{'error'} p?>" if $init->{'error'};
|
|
|
|
my $u = $init->{'journalu'};
|
|
return $ML{'talk.error.nojournal'} unless $u;
|
|
|
|
$r->notes("journalid" => $u->{'userid'});
|
|
return $LJ::MSG_READONLY_USER if LJ::get_cap($u, "readonly");
|
|
|
|
my $dbcr = LJ::get_cluster_def_reader($u);
|
|
|
|
return $LJ::MSG_READONLY_USER if $LJ::CLUSTER_DOWN{0} || ! $dbcr;
|
|
|
|
# redirect if account was renamed
|
|
if ($u->{'journaltype'} eq "R") {
|
|
LJ::load_user_props($u, "renamedto");
|
|
if ($u->{'renamedto'} ne "") {
|
|
my $id = $FORM{'itemid'}+0;
|
|
return BML::redirect(LJ::journal_base($u->{'renamedto'}) . "/$id.html?mode=reply");
|
|
}
|
|
}
|
|
|
|
my $ret = "";
|
|
|
|
my $parpost;
|
|
my $reply;
|
|
|
|
if ($init->{'replyto'})
|
|
{
|
|
my $qparentid = $init->{'replyto'};
|
|
|
|
my $sql = "SELECT t.posterid, t.nodetype, t.nodeid AS 'itemid', ".
|
|
"UNIX_TIMESTAMP()-UNIX_TIMESTAMP(t.datepost) AS 'secondsold', ".
|
|
"t.state, l.anum FROM talk2 t, log2 l WHERE l.journalid=$u->{'userid'} AND ".
|
|
"l.jitemid=t.nodeid AND t.journalid=$u->{'userid'} AND t.jtalkid=$qparentid";
|
|
foreach my $pass (1, 2) {
|
|
my $db = $pass == 1 ? LJ::get_cluster_reader($u) : $dbcr;
|
|
$parpost = $db->selectrow_hashref($sql);
|
|
last if $parpost;
|
|
}
|
|
return $ML{'.error.noreplypost'} unless $parpost;
|
|
|
|
unless ($parpost->{'nodetype'} eq "L" && $parpost->{'itemid'}) {
|
|
return "<?h1 $ML{'Error'} h1?><?p $ML{'.error.cannotreplynopost'} p?>";
|
|
}
|
|
|
|
## load its text
|
|
{
|
|
my $tt = LJ::get_talktext2($u, $init->{'replyto'});
|
|
$parpost->{'subject'} = $tt->{$init->{'replyto'}}->[0];
|
|
$parpost->{'body'} = $tt->{$init->{'replyto'}}->[1];
|
|
}
|
|
|
|
### load the talk properties
|
|
|
|
LJ::load_talk_props2($u, [ $init->{'replyto'} ], {$init->{'replyto'} => $parpost});
|
|
|
|
if($LJ::UNICODE && $parpost->{'unknown8bit'}) {
|
|
LJ::item_toutf8($u, \$parpost->{'subject'}, \$parpost->{'body'}, {});
|
|
}
|
|
|
|
$init->{'itemid'} = $parpost->{'itemid'};
|
|
$init->{'ditemid'} = $parpost->{'itemid'}*256 + $parpost->{'anum'};
|
|
}
|
|
|
|
my $itemid = $init->{'itemid'};
|
|
|
|
my $stylemine = $init->{'style'} eq "mine" ? "style=mine" : "";
|
|
|
|
## load the journal item
|
|
my $item = LJ::Talk::get_journal_item($u, $itemid);
|
|
##################################################
|
|
|
|
if ($init->{'oldurl'} && $item) {
|
|
$init->{'anum'} = $item->{'anum'};
|
|
$init->{'ditemid'} = $init->{'itemid'}*256 + $item->{'anum'};
|
|
}
|
|
|
|
unless ($item && $item->{'anum'} == $init->{'anum'}) {
|
|
BML::set_status(404); # 404 Not found
|
|
return "<?h1 $ML{'Error'} h1?><?p $ML{'talk.error.noentry'} p?>";
|
|
}
|
|
|
|
my $props = $item->{'props'};
|
|
|
|
my $ditemid = $init->{'ditemid'};
|
|
my $talkurl = LJ::journal_base($u) . "/$ditemid.html";
|
|
|
|
$parpost ||= $item; # if there's no parent post, remote is reply to top-level item
|
|
|
|
my ($up, $ur); # $up = user posted journal item; $ur = user remote is replying to
|
|
LJ::load_userids_multiple([ $item->{'posterid'} => \$up,
|
|
$parpost->{'posterid'} => \$ur, ],
|
|
[ $u ]);
|
|
|
|
my $remote = LJ::get_remote();
|
|
|
|
my @user_props = ("opt_logcommentips", "opt_whoscreened");
|
|
push @user_props, "opt_blockrobots" if $u->{'statusvis'} eq 'V';
|
|
LJ::load_user_props($u, @user_props);
|
|
if ($u->{'statusvis'} ne 'V' || $u->{'opt_blockrobots'}) {
|
|
$head = LJ::robot_meta_tags();
|
|
}
|
|
|
|
# check suspended
|
|
if ($u->{'statusvis'} eq "S" || $up->{'statusvis'} eq "S"
|
|
|| $ur && $ur->{'statusvis'} eq "S") {
|
|
BML::set_status(403); # 403 Forbidden
|
|
return "<?h1 $ML{'talk.error.suspended.title'} h1?><?p $ML{'talk.error.suspended'} p?>";
|
|
}
|
|
|
|
# check deleted
|
|
if ($u->{'statusvis'} eq "D") {
|
|
BML::set_status(404); # 404 Not found
|
|
return "<?h1 $ML{'talk.error.deleted.title'} h1?><?p $ML{'talk.error.deleted'} p?>";
|
|
}
|
|
|
|
# checked screened post
|
|
if ($parpost->{'state'} eq "S"
|
|
&& ! LJ::Talk::can_unscreen($remote, $u, $up, ($ur ? $ur->{'user'} : undef))) {
|
|
BML::set_status(403); # 403 Forbidden
|
|
return "<?h1 $ML{'Error'} h1?><?p $ML{'.error.noreply_screened'} p?>";
|
|
}
|
|
|
|
if ($parpost->{'state'} eq "D") {
|
|
BML::set_status(404); # 404 Not found
|
|
return "<?h1 $ML{'Error'} h1?><?p $ML{'.error.noreply_deleted'} p?>";
|
|
}
|
|
|
|
# check if frozen
|
|
return "<?h1 $ML{'Error'} h1?><?p $ML{'.error.noreply_frozen'} p?>"
|
|
if $parpost->{'state'} eq "F";
|
|
|
|
# don't allow anonymous comments on syndicated items
|
|
if ($u->{'journaltype'} eq "Y" && $u->{'opt_whocanreply'} eq "all") {
|
|
$u->{'opt_whocanreply'} = "reg";
|
|
}
|
|
|
|
#### Check security before viewing this post
|
|
unless (LJ::Talk::check_viewable($remote, $item, \%FORM, \$errtxt)) {
|
|
BML::set_status(403); # 403 Forbidden
|
|
return $errtxt;
|
|
}
|
|
|
|
|
|
### check If-Modified-Since
|
|
my $lastmod = $props->{'commentalter'};
|
|
my $revisiontime = $props->{' revtime'};
|
|
$lastmod = $revisiontime if $revisiontime && $revisiontime > $lastmod;
|
|
|
|
my $ims = $r->header_in("If-Modified-Since");
|
|
if ($ims) {
|
|
my $theirtime = LJ::http_to_time($ims);
|
|
if ($theirtime >= $lastmod && !$remote && $r->header_in("User-Agent") =~ /$LJ::ROBOTS_REGEXP/) {
|
|
# only for anonymous robots:
|
|
# valid browsers should refresh unique chal string!!!
|
|
BML::set_status(304); # 304 Not Modified
|
|
return "";
|
|
}
|
|
}
|
|
$r->set_last_modified($lastmod);
|
|
|
|
|
|
my $event = $FORM{'replyto'} eq "" ? $item->{'event'} : $parpost->{'body'};
|
|
my $preformatted = $FORM{'replyto'} eq "" ? $props->{'opt_preformatted'} : $parpost->{'opt_preformatted'};
|
|
|
|
LJ::CleanHTML::clean_event(\$event, $preformatted);
|
|
LJ::expand_embedded($u, $ditemid, $remote, \$event);
|
|
BML::ebml(\$event);
|
|
|
|
$ret .= "<table><tr valign='middle'>";
|
|
my $pickw = $init->{'replyto'} ? $parpost->{'picture_keyword'} : $props->{'picture_keyword'};
|
|
my $picid = LJ::get_picid_from_keyword($ur, $pickw);
|
|
|
|
my %userpics;
|
|
if ($picid) {
|
|
LJ::load_userpics(\%userpics, [ $u, $picid ]);
|
|
|
|
# not auto-vivifying $ur here because $picid is based
|
|
# on $ur existing in the first place
|
|
my $alt = $ur->{'name'};
|
|
$alt .= ": $pickw" if $pickw;
|
|
$alt = LJ::ehtml($alt);
|
|
$ret .= "<td><img src='$LJ::USERPIC_ROOT/$picid/$ur->{'userid'}' width='$userpics{$picid}->{'width'}' ".
|
|
"height='$userpics{$picid}->{'height'}' align='absmiddle' ".
|
|
"hspace='3' title='$alt' alt='' /></td>";
|
|
}
|
|
|
|
$ret .= "<td>";
|
|
|
|
# who-wrote-where
|
|
{
|
|
my $is_shared = $u->{'journaltype'} eq 'C' || $u->{'journaltype'} eq 'S';
|
|
my $suffix = $is_shared ? "_comm" : "";
|
|
|
|
# user logged in
|
|
if ($ur) {
|
|
$ret .= BML::ml("talk.somebodywrote$suffix",
|
|
{ 'realname' => LJ::ehtml($ur->{'name'}),
|
|
'userlink' => LJ::ljuser($ur),
|
|
'commlink' => LJ::ljuser($u) });
|
|
|
|
# user anonymous
|
|
} else {
|
|
$ret .= BML::ml("talk.anonwrote$suffix",
|
|
{ 'commlink' => LJ::ljuser($u) });
|
|
}
|
|
}
|
|
|
|
unless ($init->{'replyto'}) {
|
|
my $etime = $item->{'eventtime'};
|
|
$etime =~ s!(\d\d\d\d)-(\d\d)-(\d\d)!LJ::date_to_view_links($u, $&)!e;
|
|
$ret .= "<br /><font size='-1'>@ $etime</font>";
|
|
}
|
|
|
|
$ret .= "</td></tr></table>";
|
|
|
|
unless ($init->{'replyto'}) {
|
|
$ret .= LJ::Talk::link_bar({ 'u' => $u, 'up' => $up, 'headref' => \$head,
|
|
'remote' => $remote, 'itemid' => $ditemid, });
|
|
}
|
|
|
|
my %current;
|
|
if ($props->{'current_mood'} || $props->{'current_moodid'}) {
|
|
$current{'Mood'} = LJ::current_mood_str($up->{'moodthemeid'},
|
|
$props->{'current_moodid'},
|
|
$props->{'current_mood'});
|
|
}
|
|
if ($props->{'current_music'}) {
|
|
$current{'Music'} = LJ::current_music_str($props->{'current_music'});
|
|
}
|
|
|
|
$ret .= "<div style='margin-left: 30px'>";
|
|
|
|
### currents
|
|
if (! $init->{'replyto'} && %current)
|
|
{
|
|
$ret .= "<table border=0>\n";
|
|
foreach (sort keys %current) {
|
|
my $curkey = "talk.curname_" . $_;
|
|
my $curname = BML::ml($curkey);
|
|
$curname = "<b>Current $_:</b>" unless $curname;
|
|
$ret .= "<tr><td align=right>$curname</td><td>$current{$_}</td></tr>\n";
|
|
}
|
|
$ret .= "</table><p>\n";
|
|
}
|
|
|
|
### security indicator
|
|
my $sec = "";
|
|
if ($parpost->{'security'} eq "private") {
|
|
$sec = BML::fill_template("securityprivate");
|
|
} elsif ($parpost->{'security'} eq "usemask") {
|
|
$sec = BML::fill_template("securityprotected");
|
|
}
|
|
|
|
$sec .= "<br />\n" unless $sec eq "" or $parpost->{'subject'};
|
|
$ret .= $sec;
|
|
|
|
###
|
|
if ($parpost->{'subject'}) {
|
|
my $cleansubject = $parpost->{'subject'};
|
|
if ($init->{'replyto'}) {
|
|
# comments can't have HTML in subjects at all
|
|
$cleansubject = LJ::ehtml($cleansubject);
|
|
} else {
|
|
# but journal entries can have some
|
|
LJ::CleanHTML::clean_subject(\$cleansubject);
|
|
BML::ebml(\$cleansubject);
|
|
}
|
|
$ret .= "<font face=\"Arial,Helvetica\" size='+1'><i><b>$cleansubject</b></i></font><br />\n";
|
|
}
|
|
|
|
$ret .= $event;
|
|
$ret .= "</div>";
|
|
|
|
$ret .= "<br clear='all' /><hr size='2' align='center' />";
|
|
|
|
my $jarg = "journal=$u->{'user'}&";
|
|
my $readurl = LJ::Talk::talkargs($talkurl, $stylemine);
|
|
|
|
$ret .= "<p align='center' class='lesstop'><b>(<a href=\"$readurl#comments\">$ML{'talk.commentsread'}</a>)</b></p>";
|
|
|
|
# can a comment even be made?
|
|
if ($props->{'opt_nocomments'}) {
|
|
$ret .= "<?h1 $ML{'Sorry'} h1?><?p $ML{'.error.nocommentspost'} p?>";
|
|
return $ret;
|
|
}
|
|
if ($u->{'opt_showtalklinks'} eq "N") {
|
|
$ret .= "<?h1 $ML{'Sorry'} h1?><?p $ML{'.error.nocommentsjournal'} p?>";
|
|
return $ret;
|
|
}
|
|
unless (LJ::get_cap($u, "get_comments") ||
|
|
($remote && LJ::get_cap($remote, "leave_comments"))) {
|
|
$ret .= "<?h1 $ML{'Sorry'} h1?><?p ";
|
|
$ret .= $LJ::MSG_NO_COMMENT || "Sorry, you cannot leave comments at this time.";
|
|
$ret .= " p?>";
|
|
return $ret;
|
|
}
|
|
|
|
$ret .= BML::fill_template("H1", { DATA => $ML{'.postresponse'} });
|
|
|
|
$FORM{'body'} = LJ::ehtml($FORM{'body'}) if $FORM{'qr'};
|
|
|
|
$ret .= LJ::Talk::talkform({ 'remote' => $remote,
|
|
'journalu' => $u,
|
|
'parpost' => $parpost,
|
|
'replyto' => $init->{replyto},
|
|
'ditemid' => $ditemid,
|
|
'form' => \%FORM });
|
|
BML::noparse();
|
|
return $ret;
|
|
}
|
|
_code?>
|
|
|
|
<=body
|
|
head<=
|
|
<?_code return $head _code?>
|
|
<?_code return (! $LJ::REQ_HEAD_HAS{'chalresp_js'}++) ? $LJ::COMMON_CODE{'chalresp_js'} : ""; _code?>
|
|
<?_code return $LJ::COMMON_CODE{'display_none'}; _code?>
|
|
<=head
|
|
windowtitle=><?_ml /talkpost.bml.title _ml?>
|
|
page?><?_c <LJDEP>
|
|
post: htdocs/talkpost_do.bml
|
|
link: htdocs/talkread.bml, htdocs/allpics.bml, htdocs/create.bml
|
|
</LJDEP> _c?>
|
|
|