FileSha

From H&D Publishing Wiki
Revision as of 11:59, 3 November 2022 by Heerko (talk | contribs)
Screenshot 2022-10-18 at 21.05.16.png

fileSHA as protocol

André Fincato and Karl Moubarak

Why fileSHA

!/bin/bash


init: remove existing data and initialize new game-session

create file to keep track of chosen members


if [ ! -e ./.members ]; then


touch ./.members



else


rm ./.members && touch ./.members



fi




create moderation folder where to move emails


from `<mlmmj>/<list>/moderation


if [ ! -d ./moderation ]; then



mkdir ./moderation



else
 


rm -rf ./moderation && mkdir ./moderation



fi

delete .game-over mark


 rm -rf ./.game-over


← Caption: init. instructions to kick-off the game.


fileSHA is an email, “turn-based” game that uses mailing list software as its main playground–think of a chat program but it's happening over an email exchange. You send a message to the list’s email address and the message is automatically distributed to everyone on the list. The core activity of the game is file sharing. A random participant receives a prompt via email to share a file however they want. The next randomly selected participant receives that file (sometimes by coordinating with the previous user) and then decides how to use it as an input source for the file they have chosen to share. At this point, no one else in the list knows what’s occurring except the two randomly chosen participants.

The project was born of our shared curiosity and fascination with mailing lists and the role they play in bringing communities together. We were guided by an all-too-common frustration that many will have related to in recent years, that is the sudden and abrupt disappearance of online spaces that were supposed to host communities, and especially the “data” produced by their users over time. Be that a group of people gathered around a shared love for a musical genre, a team collaborating on the development of a coding framework, or a discussion board on space exploration, it’s not uncommon to see communities hosted on Mastodon or Discord[1] being closed unilaterally by their moderators, or having no way to export the “sociality” (collective memory) that’s being produced by users interaction into a data format that can be re-purposed or imported into another web service. This prompted us to ask the question:
What are other ways of communicating and navigating digital infrastructure that we might have overlooked or forgotten about?

Another inspiration for the game stems from André’s endless fascination for a piece of software called git. git propelled the Linux project[2] to become a viable, Internet-based, multiplayer effort. git uses emails as the main format for collaborating on a project, which means: mailing lists.

Looking up examples of old mailing lists on the www we found, for instance, the cryptography archives.[3] The mailing list dates back to 1970 (a Linux bug? There was no PGP software at the time, nor widespread email usage). Would an ongoing conversation thread be imaginable today, with the emergence of softwares such as Discord, an expressly community-oriented instant messaging platform? Does our frustration with online softwares have to do with these kinds of programs, or is to do with the composition and evolution of the HTTP protocol?[4]

We dreamt of working with email protocols and mailing lists, instead of the web and the HTTP protocol. What’s the UI offered by a mailing list? How easy is it to join one? What types of interactions can be designed in this space and what “social etiquettes” can be established, stretched, or ignored?

We decided to pick file sharing as the key activity in an email-based game as it aligns with another interest of ours: peer2peer computing[5]. Most p2p file-sharing software demands users to be online and at their computers at the same time, which adds an interesting requirement in the context of a non real-time technique like email: manual, human coordination. File sharing, to us, is an activity of making accessible files while simultaneously archiving them (by keeping a local copy of them on our computers). We are interested in exploring alternative methods and techniques to cloud-based file sharing or streaming software, where files continuously live online. As much as emails are easily copyable, shareable, and archivable, file sharing provides similar capabilities.

Protocol of the game

Here we have described the game in a protocolary format. While the game was originally played within email exchanges, we have tried to distill and extract most of the game’s components in such a way that it can also be played in a different format.

The original code repository with instructions can be accessed on the H&D Github page.[6]

The game is chain-based. The more people that join, the better. Five to six players is the preferred minimum. fileSHA is an “exquisite-corpse” game, which means that the next player cannot see how the previous player altered the file being shared. A classic example of an exquisite corpse is a collective drawing game where the next player receives a sheet of paper folded by the previous person, so they cannot see what’s already been drawn on the sheet.

Furthermore we added two more elements:

  • Semi-randomness[7] of selecting the next player
  • “Secrecy” between the two players exchanging the outcome

The object of the game is file sharing, meaning that each player receives the file(s) from the previous player and morphs it with one or more files of their choosing. Each player can decide how to use the previous file(s), for instance by compacting them into one file in the form of an archive (e.g., a ZIP file), or by deleting everything and sending a new, entirely different file. Nonetheless, the code we wrote keeps a record of what each participant shares, so that the process can still be revisited during and after the game finishes. So when we use the expression “file sharing technique”, we refer to the action of a player to decide how to share their file with the next player — for instance by attaching the file to the email, or using a p2p software — as well as by including a set of instructions in the email so that the next randomly chosen player can retrieve the file and keep the game going.

!/bin/bash




LIST=$1


TODO add check in case $LIST is empty string or not being passed
save to variable list of address from specified mlmmj-list
double trick:
the stdout result from the mlmmj command is flattened from a multiline print
to a one line of values divided by empty space *when* saved to a variable
we can wrap this value directly inside an array `R=()`, and let bash array
to split the string by empty space

ORIGINLIST=($(sudo /usr/bin/mlmmj-list -L /var/spool/mlmmj/$LIST))




loop over full member-list and create a new array with members
not found in ./members; those have been randomly chosen already
fairly dumb approach but works fine

CHOSEN=$(<./.members)




LISTADDRESS=()

for member in "${ORIGINLIST[@]}"; do



check if current member is NOT present in $CHOSEN (use `!`)


see <https://stackoverflow.com/a/231298>


if ! $CHOSEN =~ $member ; then


LISTADDRESS+=($member)


fi




:done


pick a random member from the list
and append it do .members
-gt => greater than; see <https://askubuntu.com/a/1042664>
SIZE=${#LISTADDRESS[@]}
if [ $SIZE -gt 0 ]; then


IDX=$((RANDOM % $SIZE))



echo ${LISTADDRESS[$IDX]} >> ./.members


echo ${LISTADDRESS[$IDX]}


else



echo "$SIZE"


fi



← Caption: pick-random-address. instructions to pick the next random player from the subscription list.

We also specifically tried to come up with activities during the game that would introduce extra degrees of “complexity”. For instance, the game ticks[8] at every seventy-two hours hours, and a new player is semi-randomly selected from the list. Sometimes a new player would be selected by choosing. Another example of adding complexity was to choose a file-sharing technique that required real-time coordination between participants (e.g. being online at the computer at the same time or through a certain period of time).

The two technologies that we chose for the game are partly or completely asynchronous (file sharing and emails), which helps to create friction within its linear-time framework (e.g., that the game is chain-based and moves from one player to the next).

These are the rules of the game:

Set up the game so that people who are interested in playing can join

In our case, the list remained open while the game was in play, meaning that someone could join mid-game and extend its duration by being semi-randomly chosen to be one of the next participants.

Set up a system to randomly pick the next player

We did this using computer software with a semi-random function (see the code snippet above the caption pick-random-address). Further rules can be added, for instance whether a participant joins early or later on in the process.

Set up a timer and game duration

We opted for seventy-two hours in a software asynchronous setting, which turned out to be too little time for the player to perform their tasks, these being: receive the file; add, remove and/or extend it; pick a file sharing method; share it with the next player.

Pick a way for the two selected players to exchange information privately

We did not use the main benefit of using mailing list software, which is to send to everyone in the list the same message. We also exploited email software by re-writing the email address of the new sender before manually sending the email to the next randomly chosen player, therefore breaking continuity.

Choose an exchange activity to complete during the game

The fact that file sharing can be interpreted quite widely contributed to unforeseen elements, which we thought could improve the overall strict linear-time experience (e.g., by having to deal with human-coordination between players, disk-space availability, etc.).

Kick off the game as the host

Start the chain of “exchange-activity” by setting an interesting example, e.g., pick a file and a method of sharing it that stirs up engagement.

Send updates to participants

If the time interval is longer than a few hours of gameplay, it might be a good idea to keep participants posted about what is going on while they are not actively playing. Of course, if the game takes place in one room, then this is probably not necessary.

Provide ways to ask for “help“ or to access the rules of the game at any time

One happy, unintended effect of using a mailing list software was the ability to use the feature of asking for “help/info” about the list: e.g., how to unsubscribe, or how to access previous messages. We used the info text to provide the basic rules of the game, and made status updates on which files had been shared so far. The “help” screen of a video game was the main source of inspiration for this feature.

 

!/bin/bash




LIST_PATH=$1


LIST_NAME=$(basename $LIST_PATH)




LIST_SENDER=$(<./.list-sender)


LIST_PREFIX=$(<$LIST_PATH/control/prefix)




read moderator email list from file and break multiline text into one line
(this is how `mailx` receives multiple recipients

MODERATORS=$(tr '\n' ' ' < "$LIST_PATH/control/owner")

GAME_OVER="game over! all subscribers have been chosen as list contributors!
"ERROR_CHAIN="An error happened; the chain order broke probably due to a mismatch in the .member list; please check!"
ERROR_NOPOST="No email has been received yet, run parse-email after a message has been posted to the list"
check if there's any email held in /moderation
we could check if $EMAIL_FN is an empty string
but it seems like eagerly asking for more troubles

MOD_N=$(ls "$LIST_PATH/moderation" | wc -l)



if [ "$MOD_N" == "0" ]; then

echo "no email held in moderation, checking subscribers list..."

CHOSEN_SIZE=$(./check-member $LIST_NAME)

if [ "$CHOSEN_SIZE" == "0" ]; then

check if game-over email was sent already
if [ -e ./.game-over ]; then

exit 1



else

touch ./.game-over



echo "$GAME_OVER"

echo "$GAME_OVER" | mailx -a "From: $LIST_SENDER" -s "$LIST_PREFIX Game Over"

$MODERATORS

fi

else


something might have happen, eg contributor did not send email within
x-time, or other things...
move on with the next contributor, if any is left
check latest email received, which we moved to ./moderation/
send message to next chosen contributor, and pray the gods

EMAIL_FN=$(ls -t "./moderation" | head -n1)

if [ -z "$EMAIL_FN" ]; then



echo "$ERROR_NOPOST"
echo "$ERROR_NOPOST" | mailx -a "From: $LIST_SENDER" -s "$LIST_PREFIX Error: no post" $MODERATORS



exit 1





else 



EMAIL_PATH="./moderation/$EMAIL_FN"




MEMBERS_LAST=$(tail -n1 .members)


pick next contributor

CONTRIBUTOR_NEXT=$(./pick-random-address $LIST_NAME)



 echo "Next contributor (1) => $CONTRIBUTOR_NEXT"






`-o` is the OR operator




if [ "$CHOSEN_SIZE" == "0" -o -z "$CONTRIBUTOR_NEXT" ]; then



echo "$ERROR_CHAIN"





send email error

echo "$ERROR_CHAIN" | mailx -a "From: $LIST_SENDER" -s "$LIST_PREFIX Error"



$MODERATORS



else


replace `To:` address
sed -i "s/^To: .*$/To: $CONTRIBUTOR_NEXT/" $EMAIL_PATH




and send email to this address
/usr/sbin/sendmail -t $CONTRIBUTOR_NEXT < $EMAIL_PATH


fi


fi

 fi



else


at least one message is present in `<mlmmj>/<list>/moderation`


fetch latest submitted email filename
<https://stackoverflow.com/a/1015687>

EMAIL_FN=$(ls -t "$LIST_PATH/moderation" | head -n1)
EMAIL_PATH="$LIST_PATH/moderation/$EMAIL_FN"


MEMBERS_LAST=$(tail -n1 .members)

FROM=$(sed -n 's/^From:.*<\(.*\)>$/\1/p' $EMAIL_PATH)



SENDER=$(<"$LIST_PATH/control/listaddress")



check if $MEMBERS_LAST is empty string (eg no contributor has been chosen yet)

if [ -z "$MEMBERS_LAST" ]; then



check if it is the first message in the chain

by checking list of chosen members


CHOSEN=$(<./.members)

CHOSEN_SIZE=${#CHOSEN[@]}



echo "CHOSEN => $CHOSEN"
echo "CHOSEN_SIZE => $CHOSEN_SIZE"



check if list of chosen members equals to 1

if [ $CHOSEN_SIZE -eq 1 ]; then



mv file out of /moderation to current dir

mv $EMAIL_PATH ./moderation/.

add address from first received email to chosen list
echo "$FROM" >> ./.members
update list of file-sharing methods shared so far

./get-subject-line $LIST_PATH



pick next contributor
CONTRIBUTOR_NEXT=$(./pick-random-address $LIST_NAME)


echo "Next contributor (2) => $CONTRIBUTOR_NEXT" 
 


replace `From:` and `To:` addresses
sed -i "s/^From: .*$/From: <$SENDER>/" "./moderation/$EMAIL_FN"

sed -i "s/^To: .*$/To: $CONTRIBUTOR_NEXT/" "./moderation/$EMAIL_FN"

and send email to this address
/usr/sbin/sendmail -t $CONTRIBUTOR_NEXT < "./moderation/$EMAIL_FN"

else

echo "something went particularly wrong, exit"
exit 1


fi
 


elif [ "$MEMBERS_LAST" == "$FROM" ]; then
 


pick next contributor

CONTRIBUTOR_NEXT=$(./pick-random-address $LIST_NAME)

`-o` is the OR operator

if [ -z "$CONTRIBUTOR_NEXT" ]; then


echo "An error happened; the chain order broke probably due to a mismatch in the .member list; please check!"


elif [ "$CONTRIBUTOR_NEXT" == "0" ]; then



check if game-over email was sent already

if [ -e ./.game-over ]; then



exit 1



else



touch ./.game-over



echo "$GAME_OVER"


echo "$GAME_OVER" | mailx -a "From: $LIST_SENDER" -s "$LIST_PREFIX Game

Over" $MODERATORS



fi



else


echo "Next contributor (3) => $CONTRIBUTOR_NEXT"
mv file out of /moderation to current dir


mv $EMAIL_PATH ./moderation/.



update list of file-sharing methods shared so far


./get-subject-line $LIST_PATH


replace `From:` and `To:` addresses
sed -i "s/^From: .*$/From: <$SENDER>/" "./moderation/$EMAIL_FN"
sed -i "s/^To: .*$/To: $CONTRIBUTOR_NEXT/" "./moderation/$EMAIL_FN"
and send email to this address

/usr/sbin/sendmail -t $CONTRIBUTOR_NEXT < "./moderation/$EMAIL_FN"



fi


else


ERROR_MISMATCH="$MEMBERS_LAST differs from $FROM. This means the user who sent the email does not match with the latest email being added to .members."

echo "$ERROR_MISMATCH"



echo "$ERROR_MISMATCH" | mailx -a "From: $LIST_SENDER" -s "$LIST_PREFIX Error"
$MODERATORS



fi



fi

← Caption: parse-email. instructions to read an incoming email held in moderation.

 

Closing

We finish with a closing remark on the often critiqued set of hydraulic metaphors—for instance: “pull,” “drain,” “consume,” “push,” “dump” a stream (of data), all the way to the extreme of “the cloud,”—which is used in computer programming by “engineers”, to talk about software that recontextualizes the domain specific language:

“Geologists have uncovered one such mechanism: rivers acting as veritable hydraulic computers (or at least, sorting machines). Rivers transport rocky materials from their point of origin (a previously created mountain subject to erosion or weathering) to the place in the ocean where these materials will accumulate. In this process, pebbles of variable size, weight and shape tend to react differently to the water transporting them. […] Once the raw materials have been sorted out into more or less homogenous groupings deposited at the bottom of the sea (that is, once they have become sedimented), a second operation is necessary to transform these loose collections of pebbles into an entity of a higher scale:
a sedimentary rock. This operation consists in cementing the sorted components together into a new entity with emergent properties of its own, that is, properties such as overall strength and permeability that cannot be ascribed to the sum of the individual pebbles.”[9]

Designing fileSHA with mailing list software gave us the space to explore the process of file sharing. Furthermore, we realized that this game has the potential to be played for an infinite amount of time. Software architectures like those of a mailing list allow for “necroposting,” We believe there is no shame in resurrecting conversations that are six months or ten years old, because at best it’s experienced as a collective sedimentation process that belongs as much to you as it does to those who wrote about it months to a decade earlier. Computers as rivers!


Karl Moubarak's bio.

André Fincato is a designer turned programmer. André joined the coop in 2017 after taking part in HDSA 2016 and then working on the H&D wiki re-organization by building a new website. His main areas of interest are: usership, p2p systems, software production, labor politics.

  1. Another important example is a web service like Instagram (owned by Facebook / Meta) shutting down user profiles (also popular ones) due to “infringing the Terms and Conditions agreement” accepted by the user to the provider upon signing up to the website. This results in a real problem for most sex workers — including famous porn stars — who make use of the service to reach out to their public as well as to create connections with other workers.
  2. Linux is a software project that launched in the early 1990s. It is the most widespread operating system used in web servers and among computer enthusiasts on “desktop.” From its conception, Linux has been entirely coordinated by sharing code through emails via the Internet.
  3. The cryptography archives: https://www.metzdowd.com/pipermail/cryptography/.
  4. HyperText Transfer Protocol is what is used to build websites and have them accessible over the Internet. If today we have broken links on the Web, is also due to specific choices taken, back in the early 1990s, when designing the way web pages should work.
  5. Expressly: when two computers directly communicate with each other over the network without a third, usually “bigger” computer acting as intermediary. Classic example is file torrenting, but also LAN parties and self-hosted email servers are common examples.
  6. https://github.com/hackersanddesigners/hd-filesha.
  7. The game picks someone from the list of participants who has not already been chosen. Plus, in a computer system, “semi-randomness” is the only option anyway.
  8. “A tick, also sometimes referred to as a jiffy, is a very small unit of time. A tick is used to determine the correct time and date on a computer.” (source https://www.computerhope.com/jargon/t/tick.htm). We use it as a verb instead of “ticking”.
  9. Manuel De Landa, “The Geology Of Morals: A Neo-Materialist Interpretation,” WORLD INFORMATION INSTITUTE, http://www.t0.or.at/delanda/geology.htm