iftechfoundation / ifdb Goto Github PK
View Code? Open in Web Editor NEWThe software behind the Interactive Fiction Database (IFDB)
License: Other
The software behind the Interactive Fiction Database (IFDB)
License: Other
https://validator.w3.org/feed/check.cgi?url=https%3A%2F%2Fifdb.org%2Fnews%3Frss
This feed does not validate.
line 10, column 13: Undefined description element: p (21 occurrences)
<description><p>IFDB now has an official <a href="/code-of-conduct">Code of ...
We're supposed to XML encode it first.
game doesn't exist
tag to any game.Delete
link under the Tags
section of the entry.Delete Tags
pop up box, click on the game doesn't exist
tag link to delete it.Save Changes
button.Nothing happens when the link is clicked. Console error is: Uncaught SyntaxError: missing ) after argument list
. After clicking on the Save Changes
button, the tag list is the same as before.
Any game doesn't exist
tag(s) should get deleted from the tag list.
https://ifdb.org/search?searchfor=tag:ghosts
"No results were found."
After reading a review, when selecting the Review Helpful checkbox "yes", it returns: You have already selected yes.
It does record the "yes" helpful but the response seems out of whack.
I ran into this problem while I was searching competitions with the string "IFComp" and wasn't getting any of the IFComp competition pages showing in the search results. To fix this problem, I tried editing one of the IFComp competition pages by adding the keyword "ifcomp" and nothing happened.
I confirmed that my keywords were set to NULL
in the keywords
column in the competitions
database table and that all keywords
values in the competitions
table were NULL
as well.
Looks like the Competition Page keywords UI was coded but the implementation was not.
For all fields in the editgame form that allow free text to be entered by users, we need to trim whitespace from both sides of the text. This will prevent two problems:
Accessing any club page results in error:
The requested club is not in the database. It might have been deleted, or the link you followed to reach this page might be broken.
This happens because the query tries to access 2 columns (password
and pswsalt
) that doesn't exist in the current sql dump.
In the current state, those 2 columns can added with empty data (it fixes the error).
https://ifdb.tads.org/search?browse sorts in Newest Listings First.
http://localhost:8080/search?browse seems to sort in a random order (probably SQL order). I see this error in the Docker log:
PHP Notice: Undefined variable: defOrderBy in /var/www/html/searchutil.php on line 826
Emails we're sending to ifdbadmin can be 1,200 characters or more. The SMTP spec says they're only allowed to be a maximum of 998 characters. https://www.php.net/manual/en/function.mail.php says "Lines should not be larger than 70 characters."
Okay, Docker is running poorly again today and I can't try this out, but here is a proposal:
There are several user privileges we are not using now, such as 'edit all formats'.
We can make it so only users with that privilege can edit embargo dates. Then, to hide a review, we only need to give that user the privilege, impersonate them, embargo the review, and then remove the privilege.
I can't test this code, but here's a suggestion:
if you go to the file 'review' in www, try replacing the current embargo code with this:
<?php
if (isset($errDetail['embargoDate']))
echo "<span class=errmsg><i>{$errDetail['embargoDate']}</i></span><br>";
$embargoPriv = false;
<b>5. Embargo date:</b>
// check the user for ADMIN and EDIT FORMATS privileges
if ($userid) {
$result = mysql_query(
"select `privileges` from users where id='$userid'", $db);
$userprivs = mysql_result($result, 0, "privileges");
$embargoPriv = (strpos($userprivs, "F") !== false);
if($embargoPriv){
echo "<input type="text" name="embargoDate" length=30 value="<?php
echo htmlspecialcharx($embargoDate) ?>"><br>";
echo " <span class=notes>Optional.
Your review and rating will be hidden from everyone
else until this date. You can use this to hide your review until a
competition is over, for example. If you don't enter a date, your
review will be published immediately. Format like this: 15-Apr-2007.
</span>";
}
else{
echo " <span class=notes>The embargo feature is currently unavailable.
</span>";
}
}
?>
</p>
I tried uploaded a non-square cover for the game. Due to the large file size, I converted it to JPEG.
The thumbnail had ugly black bars at the top and bottom. When it used a PNG (after reducing the color space), those were transparent bars, but at least it looked better.
In either case, I don't think the thumbnail should be forced into a square - if it's a rectangle, will it cause some problems with out it's displayed in various pages? If so, those can be fixed on a case-by-case basis with CSS.
dev.ifdb.org has a cron job to automagically renew its LetsEncrypt certificate, but it failed, because dev.ifdb.org is locked up behind basic authentication.
We should allow access to its .well-known
directory to allow the cron job to run normally.
https://github.com/iftechfoundation/ifdb/blob/main/www/mirrorUrl.php#L73
We have code to convert download links from http://www.ifarchive.org/if-archive/
into https://mirror.ifarchive.org/if-archive/
but it only works with www.ifarchive.org
. If the link starts with http://ifarchive.org/if-archive/
without the www.
it doesn't get converted.
That's bad, because Chrome blocks non-HTTPS download links by default.
http://localhost:8080/search?browse&list&sortby=new
An error occurred searching the database.
I noticed this issue today while researching iftechfoundation/ifdb-suggestion-tracker#289.
The functionality ofalllists
and allposts
is similar to search
, when search
is provided appropriate parameters. This fix will remove alllists
and allposts
, and replace their functionality with search
, so we have two less files to maintain and keep synced up.
The moderator emails ("new user registration" "profile change" "hyperlink review") contain links that directly perform actions in them. For example, the "new user registration" email includes links to approve, trust, or ban. All you have to do is click the link, and boom, the user is approved, trusted, or banned.
That's bad. The email link should take you to the user profile page, instead, where you can take the action there with an additional click.
Worst of all, the moderator email links don't require login. The links include randomized "nonce" temporary passwords, allowing anyone with the link to securely perform moderator actions even if/when they're not logged in. For example, here's an old link to ban a spammer ("Veronamtt," the example user from our playbook).
https://ifdb.org/userconfirm?nonce=ba5ca08b913fd9a4ad2d4fa23cc54d60&userid=jkz7zifwqfgmax63&reviewProfile=B
Anyone who clicks on that link, logged in or not, can use the "nonce" to ban Veronamtt. (Or approve Veronamt;, or trust Veronamtt.)
This might seem like an enormous security issue, but it may not be quite as serious as it looks, because the nonce passwords are only supposed to be emailed to trusted moderators, and each nonce expires pretty quickly.
Still, it's bad. I'm sure this was a very convenient system for MJR, but I'm gonna turn it off.
https://ifdb.info/tips is the 5th search result on Bing and the 4th search result on Duck Duck Go. It has a certificate error, but it's returning 200 OK.
$ curl -v http://ifdb.info/tips
< HTTP/1.1 301 Moved Permanently
< Location: https://ifdb.org/tips
$ curl -k -v https://ifdb.info/tips
< HTTP/1.1 200 OK
As seen here: https://ifdb.org/alllists?game=plvzam05bmz3enh8
The "Next" button doesnt work because the game key is missing in the url :)
IFDB uses PHP's mail()
function to send mail. https://www.php.net/manual/en/function.mail.php
Under the hood, mail()
uses sendmail
.
On the Docker image, sendmail
fails.
web_1 | sh: 1: /usr/sbin/sendmail: not found
We could probably "just" install sendmail on the web
Docker image, but in the development environment, it seems like a bad idea to send mail anyway. In the dev site, I think we want sent mails to just log to the Docker console.
In production, we probably want/need to sign up with some kind of email vendor, like Amazon SES, SparkPost, Mandril, etc. (Can PHP mail
/ sendmail
be configured to use one of those…?)
Most new issues should be filed in our IFDB Suggestion Tracker.
If you're unsure whether to file an issue here or there, prefer to file it there.
Here in this repository, the Issues tab is for bugs in existing functionality, and issues directly related to pull requests.
Launch a local dev environment with Docker at http://localhost:8080
, then open Chrome Dev Tools and paste in this script, which uses the https://ifdb.org/api/putific API to automatically submit a game.
const body = new FormData();
body.append('username', '[email protected]');
body.append('password', 'secret');
const xml = `<?xml version="1.0" encoding="UTF-8"?>
<ifindex version="1.0" xmlns="http://babel.ifarchive.org/protocol/iFiction/">
<story>
<bibliographic>
<title>Test ${Date.now()}</title>
<author>Test Author</author>
</bibliographic>
</story>
</ifindex>
`;
body.append('ifiction', new Blob([xml], {type: 'text/xml'}));
const response = await fetch('/putific', {
method: 'post',
body,
});
const {status, statusText} = response;
const text = await response.text();
console.log(JSON.stringify({status, statusText, text}, null, 2));
It works fine on localhost. But now navigate to staging https://dev.ifdb.org or production https://ifdb.org and run the same script. (Replace the username and password with your own email and password.)
You'll see this response on the console:
{
"status": 500,
"statusText": "Internal Server Error",
"text": ""
}
When I check /var/log/apache2/error.log
on staging, it says:
PHP Fatal error: Uncaught Error: Call to undefined function simplexml_load_file() in /var/www/html/putific:108\nStack trace:\n#0 /var/www/html/putific(147): load_xml_file('/tmp/phpNqpyXf', 'iFiction record')\n#1 {main}\n thrown in /var/www/html/putific on line 108, referer: https://dev.ifdb.org/
The user privileges field is an unused feature, but there's code in the admin page that parses it.
It's defined as a varchar with a default value of ''
(two single quotes) instead of an empty string. All of the users in the database have this value, except the admin, which has the value A
.
This line in the admin page attempts to access the privileges array with the value '
and fails:
for ($priv = array(), $c = 0 ; $c < strlen($privcode) ; $c++)
$priv[] = $privMap[$privcode[$c]];
The database schema should be changed to the default value of an empty string, and all of the existing users with privilege ''
should be updated to an empty string.
As we do the server transition, we'll want to ensure that we don't link to ifdb.tads.org.
I see a bunch of links to ifdb.tads.org in the database archive, and also in the code. (We especially don't want to link to ifdb.tads.org in emails we send out, e.g. new-user emails.)
Game pages (viewgame
) should include OpenGraph <meta>
tags that will improve how they appear in link previews in Twitter, Slack, Discord, and other services.
The important ones are:
og:title
- game titleog:description
- short game description (from "About the story")og:image
- game cover artHere's an example:
<head>
<meta property="og:image" content="https://ifdb.tads.org/viewgame?coverart&id=ay0yfjdivax1m40e&thumbnail=175x175" />
<meta property="og:title" content="Byzantine Perspective" />
<meta property="og:site_name" content="IFDB" />
<meta property="og:url" content="https://ifdb.tads.org/viewgame?id=ay0yfjdivax1m40e" />
<meta property="og:type" content="website" />
<meta property=" Your task is simple enough. Just nab the chalice." />
</head>
For og:image
, recommendations vary about dimensions, but I think the thumbnail is good enough.
If we add a test regular user to the local dev database, it saves a step of registering and confirming a new user via the Docker logs.
Might make automated testing a bit easier as well once we get to that point. Of course, we still have to figure out how to test registering a user, but at least this is a step in the right direction.
Mike must have run some kinda script to generate these IFArchive backups; it would strip out a bunch of tables and views, and strip columns from the users
reviewvotes
and ucomments
tables.
When the site transfers, we'll need to run that same script (or an equivalent script).
https://github.com/iftechfoundation/ifdb/blob/main/sql/patch-schema.sql#L146-L154
CREATE TABLE `reviewflags` (
`reviewid` bigint(20) NOT NULL,
`flagger` varchar(32) COLLATE latin1_german2_ci NOT NULL,
`flagtype` char(1) COLLATE latin1_german2_ci NOT NULL,
`notes` mediumtext COLLATE latin1_german2_ci,
`created` datetime NOT NULL,
KEY `reviewid` (`reviewid`),
KEY `flagger` (`flagger`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_german2_ci;
This table doesn't have a primary key. reviewid
is a foreign key to the reviews
table.
As a result, if you try to poke around this table in phpMyAdmin, it says, "Current selection does not contain a unique column. Grid edit, checkbox, Edit, Copy and Delete features are not available."
We should add an autoincrementing primary key id
to make that message go away and make it easier to work with this table.
I have an idea on how to accomplish this. In patch-schema, we currently have this:
--
-- Final view structure for view `gameRatingsSandbox0`
--
/*!50001 DROP TABLE IF EXISTS `gameRatingsSandbox0`*/;
/*!50001 DROP VIEW IF EXISTS `gameRatingsSandbox0`*/;
/*!50001 SET @saved_cs_client = @@character_set_client */;
/*!50001 SET @saved_cs_results = @@character_set_results */;
/*!50001 SET @saved_col_connection = @@collation_connection */;
/*!50001 SET character_set_client = utf8 */;
/*!50001 SET character_set_results = utf8 */;
/*!50001 SET collation_connection = utf8_general_ci */;
/*!50001 CREATE ALGORITHM=UNDEFINED */
/*!50001 VIEW `gameRatingsSandbox0` AS select `reviews`.`gameid` AS `gameid`,avg(if((ifnull(`reviews`.`RFlags`,0) & 2),NULL,`reviews`.`rating`)) AS `avgRating`,std(if((`reviews`.`RFlags` & 2),NULL,`reviews`.`rating`)) AS `stdDevRating`,count(if((`reviews`.`RFlags` & 2),NULL,`reviews`.`rating`)) AS `numRatingsInAvg`,count(`reviews`.`rating`) AS `numRatingsTotal`,count(if(isnull(`reviews`.`special`),`reviews`.`review`,NULL)) AS `numMemberReviews` from (`reviews` left join `users` on((`users`.`id` = `reviews`.`userid`))) where (ifnull((now() > `reviews`.`embargodate`),1) and (`users`.`Sandbox` in (2,3))) group by `reviews`.`gameid` */;
/*!50001 SET character_set_client = @saved_cs_client */;
/*!50001 SET character_set_results = @saved_cs_results */;
/*!50001 SET collation_connection = @saved_col_connection */;
--
-- Final view structure for view `gameRatingsSandbox01`
--
/*!50001 DROP TABLE IF EXISTS `gameRatingsSandbox01`*/;
/*!50001 DROP VIEW IF EXISTS `gameRatingsSandbox01`*/;
/*!50001 SET @saved_cs_client = @@character_set_client */;
/*!50001 SET @saved_cs_results = @@character_set_results */;
/*!50001 SET @saved_col_connection = @@collation_connection */;
/*!50001 SET character_set_client = utf8 */;
/*!50001 SET character_set_results = utf8 */;
/*!50001 SET collation_connection = utf8_general_ci */;
/*!50001 CREATE ALGORITHM=UNDEFINED */
/*!50001 VIEW `gameRatingsSandbox01` AS select `reviews`.`gameid` AS `gameid`,avg(if((ifnull(`reviews`.`RFlags`,0) & 2),NULL,`reviews`.`rating`)) AS `avgRating`,std(if((ifnull(`reviews`.`RFlags`,0) & 2),NULL,`reviews`.`rating`)) AS `stdDevRating`,count(if((ifnull(`reviews`.`RFlags`,0) & 2),NULL,`reviews`.`rating`)) AS `numRatingsInAvg`,count(`reviews`.`rating`) AS `numRatingsTotal`,count(if(isnull(`reviews`.`special`),`reviews`.`review`,NULL)) AS `numMemberReviews` from (`reviews` left join `users` on((`users`.`id` = `reviews`.`userid`))) where (ifnull((now() > `reviews`.`embargodate`),1) and (`users`.`Sandbox` in (0,1))) group by `reviews`.`gameid` */;
/*!50001 SET character_set_client = @saved_cs_client */;
/*!50001 SET character_set_results = @saved_cs_results */;
/*!50001 SET collation_connection = @saved_col_connection */;
If we just add an attribute for gameid (like gameid.sandbox), we can put games into sandboxes just like the users, and only show troll sandbox game ratings to troll sandbox people.
This would mean that the games appear in the database but only as having 0 ratings, 0 reviews, etc. We could improve this later on (by adding a message), but for now this would be an easy first step.
I would submit a pull request, but I don't know how to add a new attribute to a preexisting SQL database.
Each user, e.g. https://ifdb.org/showuser?id=xrln6pdkzzbje6r3 has a link to "News about games authored by" the user.
https://ifdb.org/showuser?id=xrln6pdkzzbje6r3&rss=gamenews
These feed doesn't validate according to https://validator.w3.org/feed/
Undefined description element: i
... r linked to profile</title><description><i>Cragne Manor</i> has been new ...
^
We should have a unit test framework and use it to run unit tests, e.g. on fixDesc
#103
5. Download Preferences
.IF Archive Mirror
dropdown menu, select ifarchive.smallwhitehouse.org (USA)
and Save Changes
.AnchorheadDemo.gblorb
.The download fails because it is trying to download from ifarchive.smallwhitehouse.org
which doesn't exist any more as far as I can tell.
There should not be a mirror dropdown menu. All traffic should be sent to ifarchive.org
.
This doesn't currently affect many of the download links because the functionality to change the links based on the IF Archive Mirror
profile setting isn't functioning properly. See issue #18 and iftechfoundation/ifdb-suggestion-tracker#1 for more information. That's why I had to specifically pick the demo link for Anchorhead to demonstrate the problem.
On loading the "My Activity" page, the following error message is given by the console:
GET https://ifdb.org/games.gif 404 (Not Found) ifdb.css:1
These lines were added to reviews.php:
sum(reviewvotes.vote = 'Y' and ifnull(rvu.sandbox, 0) in $sandbox) as helpful,
sum(reviewvotes.vote = 'N' and ifnull(rvu.sandbox, 0) in $sandbox) as unhelpful,
but they're still written as:
sum(reviewvotes.vote = 'Y')) as helpful,
sum(reviewvotes.vote = 'N') as unhelpful,
in allreviews. I think the definition of rvu also needs to be added:
left outer join users on users.id = reviews.userid
left outer join users rvu on rvu.id = reviewvotes.userid
My docker is basically caput, but I think this change should be fairly quick.
It is great that you have implemented a Play-online button for Adrift 5 games but unfortunately, it is also "working" for Adrift 4 games which will run but appear extremely bugged because of EXTREMELY limited backwards compatibility.
This issue will probably never be fixed as Adrift 4 and 5 are very different.
Thus 95-99% of all Adrift 4 games will appear unplayable due to "bugs" which really are caused by using the wrong interpreter.
Instead, use the Scare terp which is intended for Adrift 4 games and works pretty well.
A couple of ideas:
1a: Check the IFID of the Adrift game to determine whether it is Adrift 4 or Adrift 5. Remove Play Online for Adrift 4 games.
1b: (if above not possible): On IFDB, check if the game has tag:adrift 5 , otherwise remove Play Online button
2. Implement the Scare terp in Parchment (not your job but would be a great solution) - works only for Adrift 4 games.
I can easily find some examples of how low compatibility actually is if that is needed. Thanks!
Chrome (and possibly other browsers) has started to block http downloads originating from https sites. It leads to game downloads silently failing if the file link starts with http:// instead of https://.
Test case: https://ifdb.org/viewgame?id=j3rwlhuy6j6v79qj (click on the "from the author's site" download links)
I don't have a good suggestion how to fix it, links can't be automatically converted to https:// because all servers don't have it set up, for example the test case above. Maybe a warning message if someone tries to add a http download link?
After opening new user it tagged as pending review.
To remove this tag and being able to add a new listing run this query in mysql:
update users set profilestatus = NULL where email='[email protected]';
Is there a better way to confirm a new user?
It can be added to the readme in opening new user instructions.
We should have a test plan that ensures that everything works after we switch domains. We can also use this test plan to support major infrastructure enhancements (like PR #10) and perhaps some day as a specification for an automated test suite.
The test plan should be a set of instructions that a user could follow to manually verify that the site's major features still work:
When a user searches without typing in a search term (i.e. empty search), we do not include Sort by Relevance functionality because there is no concept of relevance in that scenario.
When a user searches using only search parameters, and no search term, Sort by Relevance functionality may or may not needed, depending on which search parameters are being used.
For example, per iftechfoundation/ifdb-suggestion-tracker#168, it makes sense to sort the search results of author:Clive Wilson
by relevance. On the other hand it does not make sense to sort the results of downloadable:yes
by relevance.
Here is the list of search parameters I think need Sort by Relevance functionality:
Note that this issue does not address how relevance is measured for each of these parameters, it only adds the functionality back in for each of these parameters. How the Sort by Relevance works can be figured out later on a case by case basis.
Steps to reproduce:
From here, two kinds of errors are visible.
Undefined variable: parent in /var/www/html/comment.php on line 106
Trying to access array offset on value of type null in /var/www/html/comment.php on line 106
IFDB depends on Akismet's PHP API and Recaptcha's PHP API. We should pull in those dependency via composer. https://getcomposer.org/
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.