mirror of
https://code.mensbeam.com/MensBeam/Arsse.git
synced 2024-12-22 21:22:40 +00:00
Abandon the new marking method
It was less accurate and turned out to be more complex rather than less.
This commit is contained in:
parent
4d0ce01acb
commit
4b3cfba495
6 changed files with 166 additions and 170 deletions
138
lib/Database.php
138
lib/Database.php
|
@ -1524,7 +1524,7 @@ class Database {
|
||||||
* If an empty column list is supplied, a count of articles matching the context is queried instead
|
* If an empty column list is supplied, a count of articles matching the context is queried instead
|
||||||
*
|
*
|
||||||
* @param string $user The user whose articles are to be queried
|
* @param string $user The user whose articles are to be queried
|
||||||
* @param RootContext $context The search context
|
* @param Context|UnionContext $context The search context
|
||||||
* @param array $cols The columns to request in the result set
|
* @param array $cols The columns to request in the result set
|
||||||
*/
|
*/
|
||||||
protected function articleQuery(string $user, RootContext $context, array $cols = ["id"]): Query {
|
protected function articleQuery(string $user, RootContext $context, array $cols = ["id"]): Query {
|
||||||
|
@ -1643,7 +1643,8 @@ class Database {
|
||||||
return $q;
|
return $q;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function articleFilter(Context $context, QueryFilter $q = null) {
|
/** Transforms a selection context for articles into a set of terms for an SQL "where" clause */
|
||||||
|
protected function articleFilter(Context $context, QueryFilter $q = null): QueryFilter {
|
||||||
$q = $q ?? new QueryFilter;
|
$q = $q ?? new QueryFilter;
|
||||||
$colDefs = $this->articleColumns();
|
$colDefs = $this->articleColumns();
|
||||||
// handle the simple context options
|
// handle the simple context options
|
||||||
|
@ -1919,11 +1920,10 @@ class Database {
|
||||||
*
|
*
|
||||||
* @param string $user The user who owns the articles to be modified
|
* @param string $user The user who owns the articles to be modified
|
||||||
* @param array $data An associative array of properties to modify. Anything not specified will remain unchanged
|
* @param array $data An associative array of properties to modify. Anything not specified will remain unchanged
|
||||||
* @param RootContext $context The query context to match articles against
|
* @param Context|UnionContext $context The query context to match articles against
|
||||||
* @param bool $updateTimestamp Whether to also update the timestamp. This should only be false if a mark is changed as a result of an automated action not taken by the user
|
* @param bool $updateTimestamp Whether to also update the timestamp. This should only be false if a mark is changed as a result of an automated action not taken by the user
|
||||||
*/
|
*/
|
||||||
public function articleMark(string $user, array $data, RootContext $context = null, bool $updateTimestamp = true): int {
|
public function articleMark(string $user, array $data, RootContext $context = null, bool $updateTimestamp = true): int {
|
||||||
// normalize requested marks
|
|
||||||
$data = [
|
$data = [
|
||||||
'read' => $data['read'] ?? null,
|
'read' => $data['read'] ?? null,
|
||||||
'starred' => $data['starred'] ?? null,
|
'starred' => $data['starred'] ?? null,
|
||||||
|
@ -1931,94 +1931,102 @@ class Database {
|
||||||
'note' => $data['note'] ?? null,
|
'note' => $data['note'] ?? null,
|
||||||
];
|
];
|
||||||
if (!isset($data['read']) && !isset($data['starred']) && !isset($data['hidden']) && !isset($data['note'])) {
|
if (!isset($data['read']) && !isset($data['starred']) && !isset($data['hidden']) && !isset($data['note'])) {
|
||||||
// no changes were requested
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
// begin a transaction
|
|
||||||
$tr = $this->begin();
|
|
||||||
$context = $context ?? new Context;
|
$context = $context ?? new Context;
|
||||||
if ($context instanceof UnionContext) {
|
$tr = $this->begin();
|
||||||
$out = 0;
|
$out = 0;
|
||||||
// if we were provided a union context, mark each context in series;
|
if (isset($data['read']) && (isset($data['starred']) || isset($data['hidden']) || isset($data['note'])) && ($context->edition() || $context->editions())) {
|
||||||
// this is atomic (due to the transaction already begun), but may
|
// if marking by edition both read and something else, do separate marks for starred, hidden, and note than for read
|
||||||
// result in multiple timestamps as well as an inaccurate output
|
// marking as read is ignored if the edition is not the latest, but the same is not true of the other two marks
|
||||||
// integer as articles may be in multiple contexts
|
|
||||||
// TODO: The above quirks could be fixed by resolving the union
|
|
||||||
// context to a single list of article IDs noting which are
|
|
||||||
// valid read marks (if editions were selected in any of the child
|
|
||||||
// contexts); this functionality is not needed yet, however
|
|
||||||
foreach ($context as $c) {
|
|
||||||
$out += $this->articleMark($user, $data, $c, $updateTimestamp);
|
|
||||||
}
|
|
||||||
$tr->commit();
|
|
||||||
return $out;
|
|
||||||
}
|
|
||||||
// prepare the subquery which selects the articles to act on
|
|
||||||
$subq = $this->articleQuery($user, $context);
|
$subq = $this->articleQuery($user, $context);
|
||||||
$subq->setWhere("(arsse_articles.note <> coalesce(?,arsse_articles.note) or arsse_articles.starred <> coalesce(?,arsse_articles.starred) or arsse_articles.read <> coalesce(?,arsse_articles.read) or arsse_articles.hidden <> coalesce(?,arsse_articles.hidden))", ["str", "bool", "bool", "bool"], [$data['note'], $data['starred'], $data['read'], $data['hidden']]);
|
$subq->setWhere("arsse_articles.read <> coalesce(?,arsse_articles.read)", "bool", $data['read']);
|
||||||
// if we're marking as read/unread by edition, we have to use a different query so that we only mark read/unread if the edition is the latest for the article
|
$q = new Query(
|
||||||
if (isset($data['read']) && ($context->edition() || $context->editions())) {
|
|
||||||
// set up the "SET" clause for the update
|
|
||||||
$setData = array_filter($data, function($v, $k) {
|
|
||||||
// filter out anyhing with a value of null (no change), as well as the "rea" key as it required special handling
|
|
||||||
return isset($v) && $k !== "read";
|
|
||||||
}, \ARRAY_FILTER_USE_BOTH);
|
|
||||||
[$set, $setTypes, $setValues] = $this->generateSet($setData, ['read' => "bool", 'starred' => "bool", 'hidden' => "bool", 'note' => "str"]);
|
|
||||||
$set = $set ? "$set, " : "";
|
|
||||||
$set .= "read = case when id in (select article from valid_read) then ? else \"read\" end";
|
|
||||||
$setTypes[] = "bool";
|
|
||||||
$setValues[] = $data['read'];
|
|
||||||
if ($updateTimestamp) {
|
|
||||||
$set .= ", marked = CURRENT_TIMESTAMP";
|
|
||||||
}
|
|
||||||
// prepare the rest of the query
|
|
||||||
[$inClause, $inTypes, $inValues] = $this->generateIn($context->editions ?: (array) $context->edition, "int");
|
|
||||||
$out = $this->db->prepare(
|
|
||||||
"WITH RECURSIVE
|
"WITH RECURSIVE
|
||||||
target_articles as (
|
target_articles(article) as (
|
||||||
{$subq->getQuery()}
|
{$subq->getQuery()}
|
||||||
),
|
|
||||||
valid_read as (
|
|
||||||
select selected_editions.article from (
|
|
||||||
select max(id) as edition, article from arsse_editions where id in ($inClause) group by article
|
|
||||||
) as selected_editions join (
|
|
||||||
SELECT max(id) as edition, article from arsse_editions group by article
|
|
||||||
) as latest_editions on selected_editions.edition = latest_editions.edition
|
|
||||||
)
|
)
|
||||||
update arsse_articles
|
update arsse_articles
|
||||||
set
|
set
|
||||||
|
\"read\" = ?,
|
||||||
|
touched = 1
|
||||||
|
where
|
||||||
|
id in (select article from target_articles)",
|
||||||
|
[$subq->getTypes(), "bool"],
|
||||||
|
[$subq->getValues(), $data['read']]
|
||||||
|
);
|
||||||
|
$this->db->prepare($q->getQuery(), $q->getTypes())->run($q->getValues());
|
||||||
|
// get the articles associated with the requested editions
|
||||||
|
if ($context->edition()) {
|
||||||
|
$context->article($this->articleValidateEdition($user, $context->edition)['article'])->edition(null);
|
||||||
|
} else {
|
||||||
|
$context->articles($this->editionArticle(...$context->editions))->editions(null);
|
||||||
|
}
|
||||||
|
// set starred, hidden, and/or note marks (unless all requested editions actually do not exist)
|
||||||
|
if ($context->article || $context->articles) {
|
||||||
|
$setData = array_filter($data, function($v) {
|
||||||
|
return isset($v);
|
||||||
|
});
|
||||||
|
[$set, $setTypes, $setValues] = $this->generateSet($setData, ['starred' => "bool", 'hidden' => "bool", 'note' => "str"]);
|
||||||
|
$subq = $this->articleQuery($user, $context);
|
||||||
|
$subq->setWhere("(arsse_articles.note <> coalesce(?,arsse_articles.note) or arsse_articles.starred <> coalesce(?,arsse_articles.starred) or arsse_articles.hidden <> coalesce(?,arsse_articles.hidden))", ["str", "bool", "bool"], [$data['note'], $data['starred'], $data['hidden']]);
|
||||||
|
$q = new Query(
|
||||||
|
"WITH RECURSIVE
|
||||||
|
target_articles(article) as (
|
||||||
|
{$subq->getQuery()}
|
||||||
|
)
|
||||||
|
update arsse_articles
|
||||||
|
set
|
||||||
|
touched = 1,
|
||||||
$set
|
$set
|
||||||
where
|
where
|
||||||
id in (select id from target_articles)",
|
id in (select article from target_articles)",
|
||||||
$subq->getTypes(), $inTypes, $setTypes
|
[$subq->getTypes(), $setTypes],
|
||||||
)->run(
|
[$subq->getValues(), $setValues]
|
||||||
$subq->getValues(), $inValues, $setValues
|
);
|
||||||
)->changes();
|
$this->db->prepare($q->getQuery(), $q->getTypes())->run($q->getValues());
|
||||||
|
}
|
||||||
|
// finally set the modification date for all touched marks and return the number of affected marks
|
||||||
|
if ($updateTimestamp) {
|
||||||
|
$out = $this->db->query("UPDATE arsse_articles set marked = CURRENT_TIMESTAMP, touched = 0 where touched = 1")->changes();
|
||||||
} else {
|
} else {
|
||||||
// set up the "SET" clause for the update
|
$out = $this->db->query("UPDATE arsse_articles set touched = 0 where touched = 1")->changes();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (!isset($data['read']) && ($context->edition() || $context->editions())) {
|
||||||
|
// get the articles associated with the requested editions
|
||||||
|
if ($context->edition()) {
|
||||||
|
$context->article($this->articleValidateEdition($user, $context->edition)['article'])->edition(null);
|
||||||
|
} else {
|
||||||
|
$context->articles($this->editionArticle(...$context->editions))->editions(null);
|
||||||
|
}
|
||||||
|
if (!$context->article && !$context->articles) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
$setData = array_filter($data, function($v) {
|
$setData = array_filter($data, function($v) {
|
||||||
// filter out anyhing with a value of null (no change)
|
|
||||||
return isset($v);
|
return isset($v);
|
||||||
});
|
});
|
||||||
[$set, $setTypes, $setValues] = $this->generateSet($setData, ['read' => "bool", 'starred' => "bool", 'hidden' => "bool", 'note' => "str"]);
|
[$set, $setTypes, $setValues] = $this->generateSet($setData, ['read' => "bool", 'starred' => "bool", 'hidden' => "bool", 'note' => "str"]);
|
||||||
if ($updateTimestamp) {
|
if ($updateTimestamp) {
|
||||||
$set .= ", marked = CURRENT_TIMESTAMP";
|
$set .= ", marked = CURRENT_TIMESTAMP";
|
||||||
}
|
}
|
||||||
// prepare the rest of the query
|
$subq = $this->articleQuery($user, $context);
|
||||||
$out = $this->db->prepare(
|
$subq->setWhere("(arsse_articles.note <> coalesce(?,arsse_articles.note) or arsse_articles.starred <> coalesce(?,arsse_articles.starred) or arsse_articles.read <> coalesce(?,arsse_articles.read) or arsse_articles.hidden <> coalesce(?,arsse_articles.hidden))", ["str", "bool", "bool", "bool"], [$data['note'], $data['starred'], $data['read'], $data['hidden']]);
|
||||||
|
$q = new Query(
|
||||||
"WITH RECURSIVE
|
"WITH RECURSIVE
|
||||||
target_articles as (
|
target_articles(article) as (
|
||||||
{$subq->getQuery()}
|
{$subq->getQuery()}
|
||||||
)
|
)
|
||||||
update arsse_articles
|
update arsse_articles
|
||||||
set
|
set
|
||||||
$set
|
$set
|
||||||
where
|
where
|
||||||
id in (select id from target_articles)",
|
id in (select article from target_articles)",
|
||||||
$subq->getTypes(), $setTypes
|
[$subq->getTypes(), $setTypes],
|
||||||
)->run(
|
[$subq->getValues(), $setValues]
|
||||||
$subq->getValues(), $setValues
|
);
|
||||||
)->changes();
|
$out = $this->db->prepare($q->getQuery(), $q->getTypes())->run($q->getValues())->changes();
|
||||||
}
|
}
|
||||||
$tr->commit();
|
$tr->commit();
|
||||||
return $out;
|
return $out;
|
||||||
|
|
|
@ -38,6 +38,7 @@ alter table arsse_articles add column subscription bigint unsigned;
|
||||||
alter table arsse_articles add column "read" smallint not null default 0;
|
alter table arsse_articles add column "read" smallint not null default 0;
|
||||||
alter table arsse_articles add column starred smallint not null default 0;
|
alter table arsse_articles add column starred smallint not null default 0;
|
||||||
alter table arsse_articles add column hidden smallint not null default 0;
|
alter table arsse_articles add column hidden smallint not null default 0;
|
||||||
|
alter table arsse_articles add column touched smallint not null default 0;
|
||||||
alter table arsse_articles add column marked datetime(0);
|
alter table arsse_articles add column marked datetime(0);
|
||||||
alter table arsse_articles add column note longtext;
|
alter table arsse_articles add column note longtext;
|
||||||
|
|
||||||
|
|
|
@ -35,6 +35,7 @@ alter table arsse_articles add column subscription bigint references arsse_subsc
|
||||||
alter table arsse_articles add column read smallint not null default 0;
|
alter table arsse_articles add column read smallint not null default 0;
|
||||||
alter table arsse_articles add column starred smallint not null default 0;
|
alter table arsse_articles add column starred smallint not null default 0;
|
||||||
alter table arsse_articles add column hidden smallint not null default 0;
|
alter table arsse_articles add column hidden smallint not null default 0;
|
||||||
|
alter table arsse_articles add column touched smallint not null default 0;
|
||||||
alter table arsse_articles add column marked timestamp(0) without time zone;
|
alter table arsse_articles add column marked timestamp(0) without time zone;
|
||||||
alter table arsse_articles add column note text collate "und-x-icu" not null default '';
|
alter table arsse_articles add column note text collate "und-x-icu" not null default '';
|
||||||
|
|
||||||
|
|
|
@ -48,6 +48,7 @@ create table arsse_articles_new(
|
||||||
url_title_hash text not null, -- hash of URL + title; used when checking for updates and for identification if there is no guid
|
url_title_hash text not null, -- hash of URL + title; used when checking for updates and for identification if there is no guid
|
||||||
url_content_hash text not null, -- hash of URL + content + enclosure URL + enclosure content type; used when checking for updates and for identification if there is no guid
|
url_content_hash text not null, -- hash of URL + content + enclosure URL + enclosure content type; used when checking for updates and for identification if there is no guid
|
||||||
title_content_hash text not null, -- hash of title + content + enclosure URL + enclosure content type; used when checking for updates and for identification if there is no guid
|
title_content_hash text not null, -- hash of title + content + enclosure URL + enclosure content type; used when checking for updates and for identification if there is no guid
|
||||||
|
touched int not null default 0, -- field used internally while marking; should normally be left as 0
|
||||||
note text not null default '' -- Tiny Tiny RSS freeform user note
|
note text not null default '' -- Tiny Tiny RSS freeform user note
|
||||||
);
|
);
|
||||||
insert into arsse_articles_new
|
insert into arsse_articles_new
|
||||||
|
@ -68,6 +69,7 @@ insert into arsse_articles_new
|
||||||
a.url_title_hash,
|
a.url_title_hash,
|
||||||
a.url_content_hash,
|
a.url_content_hash,
|
||||||
a.title_content_hash,
|
a.title_content_hash,
|
||||||
|
0,
|
||||||
coalesce(m.note,'')
|
coalesce(m.note,'')
|
||||||
from arsse_articles_map as i
|
from arsse_articles_map as i
|
||||||
left join arsse_articles as a on a.id = i.article
|
left join arsse_articles as a on a.id = i.article
|
||||||
|
|
|
@ -515,11 +515,20 @@ trait SeriesArticle {
|
||||||
103 => 103,
|
103 => 103,
|
||||||
104 => 104,
|
104 => 104,
|
||||||
105 => 105,
|
105 => 105,
|
||||||
|
119 => 119,
|
||||||
|
120 => 120,
|
||||||
202 => 102,
|
202 => 102,
|
||||||
203 => 103,
|
203 => 103,
|
||||||
204 => 104,
|
204 => 104,
|
||||||
205 => 105,
|
205 => 105,
|
||||||
305 => 105,
|
305 => 105,
|
||||||
|
501 => 501,
|
||||||
|
502 => 502,
|
||||||
|
519 => 519,
|
||||||
|
520 => 520,
|
||||||
|
801 => 801,
|
||||||
|
802 => 802,
|
||||||
|
902 => 802,
|
||||||
1001 => 20,
|
1001 => 20,
|
||||||
];
|
];
|
||||||
$act = Arsse::$db->editionArticle(...range(1, 1001));
|
$act = Arsse::$db->editionArticle(...range(1, 1001));
|
||||||
|
@ -580,9 +589,9 @@ trait SeriesArticle {
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][20][1] = 0;
|
$state['arsse_articles']['rows'][20][1] = 0;
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][20][4] = $now;
|
||||||
$state['arsse_articles']['rows'][22][1] = 0;
|
$state['arsse_articles']['rows'][22][1] = 0;
|
||||||
$state['arsse_articles']['rows'][11][4] = $now;
|
$state['arsse_articles']['rows'][22][4] = $now;
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -590,14 +599,12 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => true]);
|
Arsse::$db->articleMark($this->user, ['read' => true]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][8][2] = 1;
|
$state['arsse_articles']['rows'][19] = [119,1,0,0,$now,"ook"];
|
||||||
$state['arsse_articles']['rows'][8][4] = $now;
|
$state['arsse_articles']['rows'][21] = [203,1,1,0,$now,"ack"];
|
||||||
$state['arsse_articles']['rows'][10][2] = 1;
|
$state['arsse_articles']['rows'][23] = [205,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][10][4] = $now;
|
$state['arsse_articles']['rows'][24] = [206,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,5,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][25] = [207,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,6,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][26] = [208,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [14,7,1,0,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,8,1,0,$now,'',0];
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -605,10 +612,10 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['starred' => false]);
|
Arsse::$db->articleMark($this->user, ['starred' => false]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][10][3] = 0;
|
$state['arsse_articles']['rows'][21][2] = 0;
|
||||||
$state['arsse_articles']['rows'][10][4] = $now;
|
$state['arsse_articles']['rows'][21][4] = $now;
|
||||||
$state['arsse_articles']['rows'][11][3] = 0;
|
$state['arsse_articles']['rows'][22][2] = 0;
|
||||||
$state['arsse_articles']['rows'][11][4] = $now;
|
$state['arsse_articles']['rows'][22][4] = $now;
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -616,14 +623,12 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['starred' => true]);
|
Arsse::$db->articleMark($this->user, ['starred' => true]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][8][3] = 1;
|
$state['arsse_articles']['rows'][19] = [119,0,1,0,$now,"ook"];
|
||||||
$state['arsse_articles']['rows'][8][4] = $now;
|
$state['arsse_articles']['rows'][20] = [120,1,1,0,$now,"eek"];
|
||||||
$state['arsse_articles']['rows'][9][3] = 1;
|
$state['arsse_articles']['rows'][23] = [205,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][24] = [206,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,5,0,1,$now,'',0];
|
$state['arsse_articles']['rows'][25] = [207,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,6,0,1,$now,'',0];
|
$state['arsse_articles']['rows'][26] = [208,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [14,7,0,1,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,8,0,1,$now,'',0];
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -631,13 +636,9 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => false,'starred' => false]);
|
Arsse::$db->articleMark($this->user, ['read' => false,'starred' => false]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][9][2] = 0;
|
$state['arsse_articles']['rows'][20] = [120,0,0,0,$now,"eek"];
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][21] = [203,0,0,0,$now,"ack"];
|
||||||
$state['arsse_articles']['rows'][10][3] = 0;
|
$state['arsse_articles']['rows'][22] = [204,0,0,0,$now,"ach"];
|
||||||
$state['arsse_articles']['rows'][10][4] = $now;
|
|
||||||
$state['arsse_articles']['rows'][11][2] = 0;
|
|
||||||
$state['arsse_articles']['rows'][11][3] = 0;
|
|
||||||
$state['arsse_articles']['rows'][11][4] = $now;
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -645,17 +646,13 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => true,'starred' => true]);
|
Arsse::$db->articleMark($this->user, ['read' => true,'starred' => true]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][8][2] = 1;
|
$state['arsse_articles']['rows'][19] = [119,1,1,0,$now,"ook"];
|
||||||
$state['arsse_articles']['rows'][8][3] = 1;
|
$state['arsse_articles']['rows'][20] = [120,1,1,0,$now,"eek"];
|
||||||
$state['arsse_articles']['rows'][8][4] = $now;
|
$state['arsse_articles']['rows'][21] = [203,1,1,0,$now,"ack"];
|
||||||
$state['arsse_articles']['rows'][9][3] = 1;
|
$state['arsse_articles']['rows'][23] = [205,1,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][24] = [206,1,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][10][2] = 1;
|
$state['arsse_articles']['rows'][25] = [207,1,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][10][4] = $now;
|
$state['arsse_articles']['rows'][26] = [208,1,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,5,1,1,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [13,6,1,1,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,7,1,1,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,8,1,1,$now,'',0];
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -663,17 +660,13 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => false,'starred' => true]);
|
Arsse::$db->articleMark($this->user, ['read' => false,'starred' => true]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][8][3] = 1;
|
$state['arsse_articles']['rows'][19] = [119,0,1,0,$now,"ook"];
|
||||||
$state['arsse_articles']['rows'][8][4] = $now;
|
$state['arsse_articles']['rows'][20] = [120,0,1,0,$now,"eek"];
|
||||||
$state['arsse_articles']['rows'][9][2] = 0;
|
$state['arsse_articles']['rows'][22] = [204,0,1,0,$now,"ach"];
|
||||||
$state['arsse_articles']['rows'][9][3] = 1;
|
$state['arsse_articles']['rows'][23] = [205,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][24] = [206,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][11][2] = 0;
|
$state['arsse_articles']['rows'][25] = [207,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][11][4] = $now;
|
$state['arsse_articles']['rows'][26] = [208,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,5,0,1,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [13,6,0,1,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,7,0,1,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,8,0,1,$now,'',0];
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -681,17 +674,13 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => true,'starred' => false]);
|
Arsse::$db->articleMark($this->user, ['read' => true,'starred' => false]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][8][2] = 1;
|
$state['arsse_articles']['rows'][19] = [119,1,0,0,$now,"ook"];
|
||||||
$state['arsse_articles']['rows'][8][4] = $now;
|
$state['arsse_articles']['rows'][21] = [203,1,0,0,$now,"ack"];
|
||||||
$state['arsse_articles']['rows'][10][2] = 1;
|
$state['arsse_articles']['rows'][22] = [204,1,0,0,$now,"ach"];
|
||||||
$state['arsse_articles']['rows'][10][3] = 0;
|
$state['arsse_articles']['rows'][23] = [205,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][10][4] = $now;
|
$state['arsse_articles']['rows'][24] = [206,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][11][3] = 0;
|
$state['arsse_articles']['rows'][25] = [207,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][11][4] = $now;
|
$state['arsse_articles']['rows'][26] = [208,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,5,1,0,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [13,6,1,0,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,7,1,0,$now,'',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,8,1,0,$now,'',0];
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -699,18 +688,14 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['note' => "New note"]);
|
Arsse::$db->articleMark($this->user, ['note' => "New note"]);
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][8][5] = "New note";
|
$state['arsse_articles']['rows'][19] = [119,0,0,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][8][4] = $now;
|
$state['arsse_articles']['rows'][20] = [120,1,0,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][9][5] = "New note";
|
$state['arsse_articles']['rows'][21] = [203,0,1,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][22] = [204,1,1,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][10][5] = "New note";
|
$state['arsse_articles']['rows'][23] = [205,0,0,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][10][4] = $now;
|
$state['arsse_articles']['rows'][24] = [206,0,0,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][11][5] = "New note";
|
$state['arsse_articles']['rows'][25] = [207,0,0,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][11][4] = $now;
|
$state['arsse_articles']['rows'][26] = [208,0,0,0,$now,"New note"];
|
||||||
$state['arsse_articles']['rows'][] = [13,5,0,0,$now,'New note',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [13,6,0,0,$now,'New note',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,7,0,0,$now,'New note',0];
|
|
||||||
$state['arsse_articles']['rows'][] = [14,8,0,0,$now,'New note',0];
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -718,10 +703,10 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => true], (new Context)->folder(7));
|
Arsse::$db->articleMark($this->user, ['read' => true], (new Context)->folder(7));
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][] = [13,5,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][23] = [205,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,6,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][24] = [206,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [14,7,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][25] = [207,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [14,8,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][26] = [208,1,0,0,$now,""];
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -729,8 +714,8 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => true], (new Context)->folder(8));
|
Arsse::$db->articleMark($this->user, ['read' => true], (new Context)->folder(8));
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][] = [13,5,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][23] = [205,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,6,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][24] = [206,1,0,0,$now,""];
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -743,8 +728,8 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['read' => true], (new Context)->subscription(13));
|
Arsse::$db->articleMark($this->user, ['read' => true], (new Context)->subscription(13));
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][] = [13,5,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][23] = [205,1,0,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [13,6,1,0,$now,'',0];
|
$state['arsse_articles']['rows'][24] = [206,1,0,0,$now,""];
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -757,18 +742,17 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['starred' => true], (new Context)->article(120));
|
Arsse::$db->articleMark($this->user, ['starred' => true], (new Context)->article(120));
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][20][3] = 1;
|
$state['arsse_articles']['rows'][20][2] = 1;
|
||||||
$state['arsse_articles']['rows'][20][4] = $now;
|
$state['arsse_articles']['rows'][20][4] = $now;
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function testMarkMultipleArticles(): void {
|
public function testMarkMultipleArticles(): void {
|
||||||
Arsse::$db->articleMark($this->user, ['starred' => true], (new Context)->articles([2,4,7,20]));
|
Arsse::$db->articleMark($this->user, ['starred' => true], (new Context)->articles([202,204,207,120]));
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][9][3] = 1;
|
$state['arsse_articles']['rows'][20] = [120,1,1,0,$now,"eek"];
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][25] = [207,0,1,0,$now,""];
|
||||||
$state['arsse_articles']['rows'][] = [14,7,0,1,$now,'',0];
|
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -787,7 +771,7 @@ trait SeriesArticle {
|
||||||
|
|
||||||
public function testMarkTooManyMultipleArticles(): void {
|
public function testMarkTooManyMultipleArticles(): void {
|
||||||
$setSize = (new \ReflectionClassConstant(Database::class, "LIMIT_SET_SIZE"))->getValue();
|
$setSize = (new \ReflectionClassConstant(Database::class, "LIMIT_SET_SIZE"))->getValue();
|
||||||
$this->assertSame(7, Arsse::$db->articleMark($this->user, ['read' => false,'starred' => true], (new Context)->articles(range(1, $setSize * 3))));
|
$this->assertSame(7, Arsse::$db->articleMark($this->user, ['read' => false,'starred' => true], (new Context)->articles(range(119, $setSize * 3))));
|
||||||
}
|
}
|
||||||
|
|
||||||
public function testMarkAMissingArticle(): void {
|
public function testMarkAMissingArticle(): void {
|
||||||
|
@ -799,8 +783,8 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark($this->user, ['starred' => true], (new Context)->edition(1101));
|
Arsse::$db->articleMark($this->user, ['starred' => true], (new Context)->edition(1101));
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][9][3] = 1;
|
$state['arsse_articles']['rows'][20][2] = 1;
|
||||||
$state['arsse_articles']['rows'][9][4] = $now;
|
$state['arsse_articles']['rows'][20][4] = $now;
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1097,8 +1081,8 @@ trait SeriesArticle {
|
||||||
Arsse::$db->articleMark("jane.doe@example.com", ['hidden' => true], (new Context)->edition(520));
|
Arsse::$db->articleMark("jane.doe@example.com", ['hidden' => true], (new Context)->edition(520));
|
||||||
$now = Date::transform(time(), "sql");
|
$now = Date::transform(time(), "sql");
|
||||||
$state = $this->primeExpectations($this->data, $this->checkTables);
|
$state = $this->primeExpectations($this->data, $this->checkTables);
|
||||||
$state['arsse_articles']['rows'][3][6] = 1;
|
$state['arsse_articles']['rows'][13][3] = 1;
|
||||||
$state['arsse_articles']['rows'][3][4] = $now;
|
$state['arsse_articles']['rows'][13][4] = $now;
|
||||||
$this->compareExpectations(static::$drv, $state);
|
$this->compareExpectations(static::$drv, $state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -295,14 +295,14 @@ QUERY_TEXT
|
||||||
]
|
]
|
||||||
],
|
],
|
||||||
'arsse_articles' => [
|
'arsse_articles' => [
|
||||||
'columns' => ["id", "subscription", "read", "starred", "hidden", "published", "edited", "modified", "marked", "url", "title", "author", "guid", "url_title_hash", "url_content_hash", "title_content_hash", "note"],
|
'columns' => ["id", "subscription", "read", "starred", "hidden", "touched", "published", "edited", "modified", "marked", "url", "title", "author", "guid", "url_title_hash", "url_content_hash", "title_content_hash", "note"],
|
||||||
'rows' => [
|
'rows' => [
|
||||||
[1, 1, 1, 1, 0, "2001-11-08 22:07:55", "2002-11-08 07:51:12", "2001-11-08 23:44:56", "2002-11-08 00:37:22", "https://example.com/1", "Article 1", "John Doe", "GUID1", "UTHASH1", "UCHASH1", "TCHASH1", "Note 1"],
|
[1, 1, 1, 1, 0, 0, "2001-11-08 22:07:55", "2002-11-08 07:51:12", "2001-11-08 23:44:56", "2002-11-08 00:37:22", "https://example.com/1", "Article 1", "John Doe", "GUID1", "UTHASH1", "UCHASH1", "TCHASH1", "Note 1"],
|
||||||
[2, 1, 0, 0, 0, "2001-11-09 22:07:55", "2002-11-09 07:51:12", "2001-11-09 23:44:56", null, "https://example.com/2", "Article 2", "Jane Doe", "GUID2", "UTHASH2", "UCHASH2", "TCHASH2", ""],
|
[2, 1, 0, 0, 0, 0, "2001-11-09 22:07:55", "2002-11-09 07:51:12", "2001-11-09 23:44:56", null, "https://example.com/2", "Article 2", "Jane Doe", "GUID2", "UTHASH2", "UCHASH2", "TCHASH2", ""],
|
||||||
[7, 4, 1, 0, 0, "2001-11-12 22:07:55", "2002-11-12 07:51:12", "2001-11-12 23:44:56", "2002-11-12 00:37:22", "https://example.net/1", "Article 5", "Adam Doe", "GUID5", "UTHASH5", "UCHASH5", "TCHASH5", "Note 5"],
|
[7, 4, 1, 0, 0, 0, "2001-11-12 22:07:55", "2002-11-12 07:51:12", "2001-11-12 23:44:56", "2002-11-12 00:37:22", "https://example.net/1", "Article 5", "Adam Doe", "GUID5", "UTHASH5", "UCHASH5", "TCHASH5", "Note 5"],
|
||||||
[8, 6, 0, 1, 0, "2001-11-12 22:07:55", "2002-11-12 07:51:12", "2001-11-12 23:44:56", "2002-12-12 00:37:22", "https://example.net/1", "Article 5", "Adam Doe", "GUID5", "UTHASH5", "UCHASH5", "TCHASH5", ""],
|
[8, 6, 0, 1, 0, 0, "2001-11-12 22:07:55", "2002-11-12 07:51:12", "2001-11-12 23:44:56", "2002-12-12 00:37:22", "https://example.net/1", "Article 5", "Adam Doe", "GUID5", "UTHASH5", "UCHASH5", "TCHASH5", ""],
|
||||||
[9, 4, 0, 0, 0, "2001-11-13 22:07:55", "2002-11-13 07:51:12", "2001-11-13 23:44:56", null, "https://example.net/2", "Article 6", "Evie Doe", "GUID6", "UTHASH6", "UCHASH6", "TCHASH6", ""],
|
[9, 4, 0, 0, 0, 0, "2001-11-13 22:07:55", "2002-11-13 07:51:12", "2001-11-13 23:44:56", null, "https://example.net/2", "Article 6", "Evie Doe", "GUID6", "UTHASH6", "UCHASH6", "TCHASH6", ""],
|
||||||
[10, 6, 0, 0, 1, "2001-11-13 22:07:55", "2002-11-13 07:51:12", "2001-11-13 23:44:56", "2002-12-13 00:37:22", "https://example.net/2", "Article 6", "Evie Doe", "GUID6", "UTHASH6", "UCHASH6", "TCHASH6", "Note 6"],
|
[10, 6, 0, 0, 1, 0, "2001-11-13 22:07:55", "2002-11-13 07:51:12", "2001-11-13 23:44:56", "2002-12-13 00:37:22", "https://example.net/2", "Article 6", "Evie Doe", "GUID6", "UTHASH6", "UCHASH6", "TCHASH6", "Note 6"],
|
||||||
]
|
]
|
||||||
],
|
],
|
||||||
'arsse_article_contents' => [
|
'arsse_article_contents' => [
|
||||||
|
|
Loading…
Reference in a new issue