From 19da22e14448581bf8f36f5e74c0628870e1f5d7 Mon Sep 17 00:00:00 2001 From: "J. King" Date: Sun, 5 Feb 2023 09:26:59 -0500 Subject: [PATCH] Initial work on refactoring article tests --- lib/Database.php | 62 ++++---- tests/cases/Database/AbstractTest.php | 2 +- tests/cases/Database/SeriesArticle.php | 202 ++++++++++++------------- 3 files changed, 125 insertions(+), 141 deletions(-) diff --git a/lib/Database.php b/lib/Database.php index a57d9a16..0bd95254 100644 --- a/lib/Database.php +++ b/lib/Database.php @@ -200,7 +200,7 @@ class Database { * The clause is structured such that all terms must be present across any of the columns * * @param string[] $terms The terms to search for - * @param string[] $cols The columns to match against; these are -not- sanitized, so much -not- come directly from user input + * @param string[] $cols The columns to match against; these are -not- sanitized, so must -not- come directly from user input * @param boolean $matchAny Whether the search is successful when it matches any (true) or all (false) terms */ protected function generateSearch(array $terms, array $cols, bool $matchAny = false): array { @@ -1489,34 +1489,34 @@ class Database { $greatest = $this->db->sqlToken("greatest"); $least = $this->db->sqlToken("least"); return [ - 'id' => "arsse_articles.id", // The article's unchanging numeric ID - 'edition' => "latest_editions.edition", // The article's numeric ID which increases each time it is modified in the feed - 'latest_edition' => "max(latest_editions.edition)", // The most recent of all editions - 'url' => "arsse_articles.url", // The URL of the article's full content - 'title' => "arsse_articles.title", // The title - 'author' => "arsse_articles.author", // The name of the author - 'content' => "arsse_article_contents.content", // The article content - 'guid' => "arsse_articles.guid", // The GUID of the article, as presented in the feed (NOTE: Picofeed actually provides a hash of the ID) - 'fingerprint' => "arsse_articles.url_title_hash || ':' || arsse_articles.url_content_hash || ':' || arsse_articles.title_content_hash", // A combination of three hashes - 'folder' => "coalesce(arsse_subscriptions.folder,0)", // The folder of the article's feed. This is mainly for use in WHERE clauses - 'top_folder' => "coalesce(folder_data.top,0)", // The top-most folder of the article's feed. This is mainly for use in WHERE clauses - 'folder_name' => "folder_data.name", // The name of the folder of the article's feed. This is mainly for use in WHERE clauses - 'top_folder_name' => "folder_data.top_name", // The name of the top-most folder of the article's feed. This is mainly for use in WHERE clauses - 'subscription' => "arsse_subscriptions.id", // The article's parent subscription - 'feed' => "arsse_subscriptions.feed", // The article's parent feed - 'hidden' => "coalesce(arsse_marks.hidden,0)", // Whether the article is hidden - 'starred' => "coalesce(arsse_marks.starred,0)", // Whether the article is starred - 'unread' => "abs(coalesce(arsse_marks.read,0) - 1)", // Whether the article is unread - 'labelled' => "$least(coalesce(label_stats.assigned,0),1)", // Whether the article has at least one label - 'annotated' => "(case when coalesce(arsse_marks.note,'') <> '' then 1 else 0 end)", // Whether the article has a note - 'note' => "coalesce(arsse_marks.note,'')", // The article's note, if any - 'published_date' => "arsse_articles.published", // The date at which the article was first published i.e. its creation date - 'edited_date' => "arsse_articles.edited", // The date at which the article was last edited according to the feed - 'modified_date' => "arsse_articles.modified", // The date at which the article was last updated in our database - 'marked_date' => "$greatest(arsse_articles.modified, coalesce(arsse_marks.modified, '0001-01-01 00:00:00'), coalesce(label_stats.modified, '0001-01-01 00:00:00'))", // The date at which the article metadata was last modified by the user - 'subscription_title' => "coalesce(arsse_subscriptions.title, arsse_feeds.title)", // The parent subscription's title - 'media_url' => "arsse_enclosures.url", // The URL of the article's enclosure, if any (NOTE: Picofeed only exposes one enclosure) - 'media_type' => "arsse_enclosures.type", // The Content-Type of the article's enclosure, if any + 'id' => "arsse_articles.id", // The article's unchanging numeric ID + 'edition' => "latest_editions.edition", // The article's numeric ID which increases each time it is modified in the feed + 'latest_edition' => "max(latest_editions.edition)", // The most recent of all editions + 'url' => "arsse_articles.url", // The URL of the article's full content + 'title' => "arsse_articles.title", // The title + 'author' => "arsse_articles.author", // The name of the author + 'content' => "arsse_article_contents.content", // The article content + 'guid' => "arsse_articles.guid", // The GUID of the article, as presented in the feed (NOTE: Picofeed actually provides a hash of the ID) + 'fingerprint' => "arsse_articles.url_title_hash || ':' || arsse_articles.url_content_hash || ':' || arsse_articles.title_content_hash", // A combination of three hashes + 'folder' => "coalesce(arsse_subscriptions.folder,0)", // The folder of the article's feed. This is mainly for use in WHERE clauses + 'top_folder' => "coalesce(folder_data.top,0)", // The top-most folder of the article's feed. This is mainly for use in WHERE clauses + 'folder_name' => "folder_data.name", // The name of the folder of the article's feed. This is mainly for use in WHERE clauses + 'top_folder_name' => "folder_data.top_name", // The name of the top-most folder of the article's feed. This is mainly for use in WHERE clauses + 'subscription' => "arsse_subscriptions.id", // The article's parent subscription + 'feed' => "arsse_subscriptions.feed", // The article's parent feed + 'hidden' => "coalesce(arsse_articles.hidden,0)", // Whether the article is hidden + 'starred' => "coalesce(arsse_articles.starred,0)", // Whether the article is starred + 'unread' => "abs(coalesce(arsse_articles.read,0) - 1)", // Whether the article is unread + 'labelled' => "$least(coalesce(label_stats.assigned,0),1)", // Whether the article has at least one label + 'annotated' => "(case when coalesce(arsse_articles.note,'') <> '' then 1 else 0 end)", // Whether the article has a note + 'note' => "coalesce(arsse_articles.note,'')", // The article's note, if any + 'published_date' => "arsse_articles.published", // The date at which the article was first published i.e. its creation date + 'edited_date' => "arsse_articles.edited", // The date at which the article was last edited according to the feed + 'modified_date' => "arsse_articles.modified", // The date at which the article was last updated in our database + 'marked_date' => "$greatest(arsse_articles.modified, coalesce(arsse_articles.marked, '0001-01-01 00:00:00'), coalesce(label_stats.modified, '0001-01-01 00:00:00'))", // The date at which the article metadata was last modified by the user + 'subscription_title' => "coalesce(arsse_subscriptions.title, arsse_subscriptions.feed_title)", // The parent subscription's title + 'media_url' => "arsse_enclosures.url", // The URL of the article's enclosure, if any (NOTE: Picofeed only exposes one enclosure) + 'media_type' => "arsse_enclosures.type", // The Content-Type of the article's enclosure, if any ]; } @@ -1572,10 +1572,8 @@ class Database { select $outColumns from arsse_articles - join arsse_subscriptions on arsse_subscriptions.feed = arsse_articles.feed and arsse_subscriptions.owner = ? - join arsse_feeds on arsse_subscriptions.feed = arsse_feeds.id + join arsse_subscriptions on arsse_subscriptions.id = arsse_articles.subscription and arsse_subscriptions.owner = ? left join folder_data on arsse_subscriptions.folder = folder_data.id - left join arsse_marks on arsse_marks.subscription = arsse_subscriptions.id and arsse_marks.article = arsse_articles.id left join arsse_enclosures on arsse_enclosures.article = arsse_articles.id join ( select article, max(id) as edition from arsse_editions group by article diff --git a/tests/cases/Database/AbstractTest.php b/tests/cases/Database/AbstractTest.php index d7a17578..f7687fb8 100644 --- a/tests/cases/Database/AbstractTest.php +++ b/tests/cases/Database/AbstractTest.php @@ -22,7 +22,7 @@ abstract class AbstractTest extends \JKingWeb\Arsse\Test\AbstractTest { use SeriesSubscription; //use SeriesLabel; use SeriesTag; - //use SeriesArticle; + use SeriesArticle; //use SeriesCleanup; /** @var \JKingWeb\Arsse\Db\Driver */ diff --git a/tests/cases/Database/SeriesArticle.php b/tests/cases/Database/SeriesArticle.php index d2301e5d..e28144c7 100644 --- a/tests/cases/Database/SeriesArticle.php +++ b/tests/cases/Database/SeriesArticle.php @@ -29,24 +29,6 @@ trait SeriesArticle { ["jill.doe@example.com", "", 5], ], ], - 'arsse_feeds' => [ - 'columns' => ["id", "url", "title"], - 'rows' => [ - [1,"http://example.com/1", "Feed 1"], - [2,"http://example.com/2", "Feed 2"], - [3,"http://example.com/3", "Feed 3"], - [4,"http://example.com/4", "Feed 4"], - [5,"http://example.com/5", "Feed 5"], - [6,"http://example.com/6", "Feed 6"], - [7,"http://example.com/7", "Feed 7"], - [8,"http://example.com/8", "Feed 8"], - [9,"http://example.com/9", "Feed 9"], - [10,"http://example.com/10", "Feed 10"], - [11,"http://example.com/11", "Feed 11"], - [12,"http://example.com/12", "Feed 12"], - [13,"http://example.com/13", "Feed 13"], - ], - ], 'arsse_folders' => [ 'columns' => ["id", "owner", "parent", "name"], 'rows' => [ @@ -75,23 +57,23 @@ trait SeriesArticle { ], ], 'arsse_subscriptions' => [ - 'columns' => ["id", "owner", "feed", "folder", "title", "scrape"], + 'columns' => ["id", "owner", "url", "feed_title", "folder", "title", "scrape"], 'rows' => [ - [1, "john.doe@example.com",1, null,"Subscription 1", 0], - [2, "john.doe@example.com",2, null,null, 0], - [3, "john.doe@example.com",3, 1,"Subscription 3", 0], - [4, "john.doe@example.com",4, 6,null, 0], - [5, "john.doe@example.com",10, 5,"Subscription 5", 0], - [6, "jane.doe@example.com",1, null,null, 0], - [7, "jane.doe@example.com",10,null,"Subscription 7", 0], - [8, "john.doe@example.org",11,null,null, 0], - [9, "john.doe@example.org",12,null,"Subscription 9", 0], - [10,"john.doe@example.org",13,null,null, 0], - [11,"john.doe@example.net",10,null,"Subscription 11",0], - [12,"john.doe@example.net",2, 9,null, 0], - [13,"john.doe@example.net",3, 8,"Subscription 13",0], - [14,"john.doe@example.net",4, 7,null, 0], - [15,"jill.doe@example.com",11,null,null, 1], + [1, "john.doe@example.com","http://example.com/1", "Feed 1", null,"Subscription 1", 0], + [2, "john.doe@example.com","http://example.com/2", "Feed 2", null,null, 0], + [3, "john.doe@example.com","http://example.com/3", "Feed 3", 1,"Subscription 3", 0], + [4, "john.doe@example.com","http://example.com/4", "Feed 4", 6,null, 0], + [5, "john.doe@example.com","http://example.com/10", "Feed 10", 5,"Subscription 5", 0], + [6, "jane.doe@example.com","http://example.com/1", "Feed 1", null,null, 0], + [7, "jane.doe@example.com","http://example.com/10", "Feed 10",null,"Subscription 7", 0], + [8, "john.doe@example.org","http://example.com/11", "Feed 11",null,null, 0], + [9, "john.doe@example.org","http://example.com/12", "Feed 12",null,"Subscription 9", 0], + [10,"john.doe@example.org","http://example.com/13", "Feed 13",null,null, 0], + [11,"john.doe@example.net","http://example.com/10", "Feed 10",null,"Subscription 11",0], + [12,"john.doe@example.net","http://example.com/2", "Feed 2", 9,null, 0], + [13,"john.doe@example.net","http://example.com/3", "Feed 3", 8,"Subscription 13",0], + [14,"john.doe@example.net","http://example.com/4", "Feed 4", 7,null, 0], + [15,"jill.doe@example.com","http://example.com/11", "Feed 11",null,null, 1], ], ], 'arsse_tag_members' => [ @@ -111,83 +93,29 @@ trait SeriesArticle { ], 'arsse_articles' => [ 'columns' => [ - "id", "feed", "url", "title", "author", "published", "edited", "content", "guid", - "url_title_hash", "url_content_hash", "title_content_hash", "modified", "content_scraped", + "id", "subscription", "url", "title", "author", "published", "edited", "guid", + "url_title_hash", "url_content_hash", "title_content_hash", "modified", + "read", "starred", "marked", "note", "hidden", ], 'rows' => [ - [1,1,null,"Title one", null,null,null,"First article", null,"","","","2000-01-01T00:00:00Z",null], - [2,1,null,"Title two", null,null,null,"Second article",null,"","","","2010-01-01T00:00:00Z",null], - [3,2,null,"Title three",null,null,null,"Third article", null,"","","","2000-01-01T00:00:00Z",null], - [4,2,null,null,"John Doe",null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [5,3,null,null,"John Doe",null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [6,3,null,null,"Jane Doe",null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [7,4,null,null,"Jane Doe",null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [8,4,null,null,null,null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [9,5,null,null,null,null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [10,5,null,null,null,null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [11,6,null,null,null,null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [12,6,null,null,null,null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [13,7,null,null,null,null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [14,7,null,null,null,null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [15,8,null,null,null,null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [16,8,null,null,null,null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [17,9,null,null,null,null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [18,9,null,null,null,null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [19,10,null,null,null,null,null,null,null,"","","","2000-01-01T00:00:00Z",null], - [20,10,null,null,null,null,null,null,null,"","","","2010-01-01T00:00:00Z",null], - [101,11,'http://example.com/1','Article title 1','','2000-01-01 00:00:00','2000-01-01 00:00:01','

Article content 1

','e433653cef2e572eee4215fa299a4a5af9137b2cefd6283c85bd69a32915beda','f5cb8bfc1c7396dc9816af212a3e2ac5221585c2a00bf7ccb6aabd95dcfcd6a6','fb0bc8f8cb08913dc5a497db700e327f1d34e4987402687d494a5891f24714d4','18fdd4fa93d693128c43b004399e5c9cea6c261ddfa002518d3669f55d8c2207','2000-01-01 01:00:00',"

Scraped content 1

"], - [102,11,'http://example.com/2','Article title 2','','2000-01-02 00:00:00','2000-01-02 00:00:02','

Article content 2

','5be8a5a46ecd52ed132191c8d27fb1af6b3d4edc00234c5d9f8f0e10562ed3b7','0e86d2de822a174fe3c44a466953e63ca1f1a58a19cbf475fce0855d4e3d5153','13075894189c47ffcfafd1dfe7fbb539f7c74a69d35a399b3abf8518952714f9','2abd0a8cba83b8214a66c8f0293ba63e467d720540e29ff8ddcdab069d4f1c9e','2000-01-02 02:00:00',null], - [103,12,'http://example.com/3','Article title 3','','2000-01-03 00:00:00','2000-01-03 00:00:03','

Article content 3

','31a6594500a48b59fcc8a075ce82b946c9c3c782460d088bd7b8ef3ede97ad92','f74b06b240bd08abf4d3fdfc20dba6a6f6eb8b4f1a00e9a617efd63a87180a4b','b278380e984cefe63f0e412b88ffc9cb0befdfa06fdc00bace1da99a8daff406','ad622b31e739cd3a3f3c788991082cf4d2f7a8773773008e75f0572e58cd373b','2000-01-03 03:00:00',null], - [104,12,'http://example.com/4','Article title 4','','2000-01-04 00:00:00','2000-01-04 00:00:04','

Article content 4

','804e517d623390e71497982c77cf6823180342ebcd2e7d5e32da1e55b09dd180','f3615c7f16336d3ea242d35cf3fc17dbc4ee3afb78376bf49da2dd7a5a25dec8','f11c2b4046f207579aeb9c69a8c20ca5461cef49756ccfa5ba5e2344266da3b3','ab2da63276acce431250b18d3d49b988b226a99c7faadf275c90b751aee05be9','2000-01-04 04:00:00',null], - [105,13,'http://example.com/5','Article title 5','','2000-01-05 00:00:00','2000-01-05 00:00:05','

Article content 5

','db3e736c2c492f5def5c5da33ddcbea1824040e9ced2142069276b0a6e291a41','d40da96e39eea6c55948ccbe9b3d275b5f931298288dbe953990c5f496097022','834240f84501b5341d375414718204ec421561f3825d34c22bf9182203e42900','43b970ac6ec5f8a9647b2c7e4eed8b1d7f62e154a95eed748b0294c1256764ba','2000-01-05 05:00:00',null], + [1, 1,null, "Title one", null, null, null, null,"","","","2000-01-01T00:00:00Z",1,1,'2000-01-01 00:00:00','',0], + [2, 1,null, "Title two", null, null, null, null,"","","","2010-01-01T00:00:00Z",0,0,'2010-01-01 00:00:00','Some Note',0], + [3, 2,null, "Title three", null, null, null, "Third article", null,"","","","2000-01-01T00:00:00Z",0,0,null,'',0], + [4, 2,null, null, "John Doe",null, null, null,null,"","","","2010-01-01T00:00:00Z",0,0,null,'',0], + [5, 3,null, null, "John Doe",null, null, null,null,"","","","2000-01-01T00:00:00Z",0,0,null,'',0], + [6, 3,null, null, "Jane Doe",null, null, null,null,"","","","2010-01-01T00:00:00Z",0,0,'2000-01-01 00:00:00','',1], + [7, 4,null, null, "Jane Doe",null, null, null,null,"","","","2000-01-01T00:00:00Z",0,0,null,'',0], + [8, 4,null, null, null, null, null, null,null,"","","","2010-01-01T00:00:00Z",0,0,null,'',0], + [19, 10,null, null, null, null, null, null,null,"","","","2000-01-01T00:00:00Z",1,0,'2016-01-01 00:00:00','',0], + [20, 10,null, null, null, null, null, null,null,"","","","2010-01-01T00:00:00Z",0,1,'2005-01-01 00:00:00','',0], + [101, 11,'http://example.com/1','Article title 1','', '2000-01-01 00:00:00','2000-01-01 00:00:01','

Article content 1

','e433653cef2e572eee4215fa299a4a5af9137b2cefd6283c85bd69a32915beda','f5cb8bfc1c7396dc9816af212a3e2ac5221585c2a00bf7ccb6aabd95dcfcd6a6','fb0bc8f8cb08913dc5a497db700e327f1d34e4987402687d494a5891f24714d4','18fdd4fa93d693128c43b004399e5c9cea6c261ddfa002518d3669f55d8c2207','2000-01-01 01:00:00',0,0,null,'',0], + [102, 11,'http://example.com/2','Article title 2','', '2000-01-02 00:00:00','2000-01-02 00:00:02','

Article content 2

','5be8a5a46ecd52ed132191c8d27fb1af6b3d4edc00234c5d9f8f0e10562ed3b7','0e86d2de822a174fe3c44a466953e63ca1f1a58a19cbf475fce0855d4e3d5153','13075894189c47ffcfafd1dfe7fbb539f7c74a69d35a399b3abf8518952714f9','2abd0a8cba83b8214a66c8f0293ba63e467d720540e29ff8ddcdab069d4f1c9e','2000-01-02 02:00:00',0,0,null,'',0], + [103, 12,'http://example.com/3','Article title 3','', '2000-01-03 00:00:00','2000-01-03 00:00:03','

Article content 3

','31a6594500a48b59fcc8a075ce82b946c9c3c782460d088bd7b8ef3ede97ad92','f74b06b240bd08abf4d3fdfc20dba6a6f6eb8b4f1a00e9a617efd63a87180a4b','b278380e984cefe63f0e412b88ffc9cb0befdfa06fdc00bace1da99a8daff406','ad622b31e739cd3a3f3c788991082cf4d2f7a8773773008e75f0572e58cd373b','2000-01-03 03:00:00',0,0,null,'',0], + [104, 12,'http://example.com/4','Article title 4','', '2000-01-04 00:00:00','2000-01-04 00:00:04','

Article content 4

','804e517d623390e71497982c77cf6823180342ebcd2e7d5e32da1e55b09dd180','f3615c7f16336d3ea242d35cf3fc17dbc4ee3afb78376bf49da2dd7a5a25dec8','f11c2b4046f207579aeb9c69a8c20ca5461cef49756ccfa5ba5e2344266da3b3','ab2da63276acce431250b18d3d49b988b226a99c7faadf275c90b751aee05be9','2000-01-04 04:00:00',0,0,null,'',0], + [105, 13,'http://example.com/5','Article title 5','', '2000-01-05 00:00:00','2000-01-05 00:00:05','

Article content 5

','db3e736c2c492f5def5c5da33ddcbea1824040e9ced2142069276b0a6e291a41','d40da96e39eea6c55948ccbe9b3d275b5f931298288dbe953990c5f496097022','834240f84501b5341d375414718204ec421561f3825d34c22bf9182203e42900','43b970ac6ec5f8a9647b2c7e4eed8b1d7f62e154a95eed748b0294c1256764ba','2000-01-05 05:00:00',0,0,null,'',0], + [1101,15,'http://example.com/1','Article title 1','', '2000-01-01 00:00:00','2000-01-01 00:00:01','

Article content 1

','e433653cef2e572eee4215fa299a4a5af9137b2cefd6283c85bd69a32915beda','f5cb8bfc1c7396dc9816af212a3e2ac5221585c2a00bf7ccb6aabd95dcfcd6a6','fb0bc8f8cb08913dc5a497db700e327f1d34e4987402687d494a5891f24714d4','18fdd4fa93d693128c43b004399e5c9cea6c261ddfa002518d3669f55d8c2207','2000-01-01 01:00:00',0,0,null,'',0], ], - ], - 'arsse_enclosures' => [ - 'columns' => ["article", "url", "type"], - 'rows' => [ - [102,"http://example.com/text","text/plain"], - [103,"http://example.com/video","video/webm"], - [104,"http://example.com/image","image/svg+xml"], - [105,"http://example.com/audio","audio/ogg"], - - ], - ], - 'arsse_editions' => [ - 'columns' => ["id", "article"], - 'rows' => [ - [1,1], - [2,2], - [3,3], - [4,4], - [5,5], - [6,6], - [7,7], - [8,8], - [9,9], - [10,10], - [11,11], - [12,12], - [13,13], - [14,14], - [15,15], - [16,16], - [17,17], - [18,18], - [19,19], - [20,20], - [101,101], - [102,102], - [103,103], - [104,104], - [105,105], - [202,102], - [203,103], - [204,104], - [205,105], - [305,105], - [1001,20], - ], - ], + ],/* 'arsse_marks' => [ 'columns' => ["subscription", "article", "read", "starred", "modified", "note", "hidden"], 'rows' => [ @@ -208,6 +136,62 @@ trait SeriesArticle { [6, 1,0,1,'2010-01-01 00:00:00','',1], [6, 2,1,0,'2010-01-01 00:00:00','',1], ], + ],*/ + 'arsse_article_contents' => [ + 'columns' => ["id", "content"], + 'rows' => [ + [1, 'First article'], + [2, 'Second article'], + [3, 'third article'], + [4, ''], + [5, ''], + [6, ''], + [7, ''], + [8, ''], + [19, ''], + [20, ''], + [101,'

Article content 1

'], + [102,'

Article content 2

'], + [103,'

Article content 3

'], + [104,'

Article content 4

'], + [105,'

Article content 5

'], + [1101,"

Scraped content 1

"], + ], + ], + 'arsse_enclosures' => [ + 'columns' => ["article", "url", "type"], + 'rows' => [ + [102,"http://example.com/text","text/plain"], + [103,"http://example.com/video","video/webm"], + [104,"http://example.com/image","image/svg+xml"], + [105,"http://example.com/audio","audio/ogg"], + ], + ], + 'arsse_editions' => [ + 'columns' => ["id", "article"], + 'rows' => [ + [1,1], + [2,2], + [3,3], + [4,4], + [5,5], + [6,6], + [7,7], + [8,8], + [19,19], + [20,20], + [101,101], + [102,102], + [103,103], + [104,104], + [105,105], + [202,102], + [203,103], + [204,104], + [205,105], + [305,105], + [1001,20], + ], ], 'arsse_categories' => [ // author-supplied categories 'columns' => ["article", "name"], @@ -1128,3 +1112,5 @@ trait SeriesArticle { $this->assertResult($exp, Arsse::$db->articleList("jill.doe@example.com", (new Context)->subscription(15)->searchTerms(["scraped"]), ["id", "content"])); } } + +}