Over the last three decades, the Internet has mushroomed from 0 to 4.6 billion active “users”, 60 per cent of the world population (and more than 90 per cent in the developed world), the fastest diffusion in human history. But what kind of “society” has it created? The digital realm includes a few powerful entities, who control the entire space, and billions of “data subjects”, as termed by the EU’s General Data Protection Regulation (GDPR), who have almost no rights and cannot vote, be consulted, or influence decision-making. They have no due process (e.g., in censorship, account blocking, or privacy violation) and are not the owners of their data. The structure of the digital space remains “feudal” in nature—people are not even perceived as digital “citizens” but as “users”—and it is not based on the ideals on which citizenship in democracies is grounded: liberty, equality, and popular sovereignty. The digital space is further rampant with sybils (fake/duplicate accounts) and bots, making it a hostile environment and untenable for democratic governance. To a large extent, digital technology is the great unequalizer in today’s world, making a few digital “barons” rich and powerful by profiting from the multitudes performing digital labour without compensation. Like feudal lords of yore, the digital barons set their platform’s rules of conduct (legislative), interpretation (judicial), and implementation (executive), and violate the dictum “no taxation without representation”. New technologies do not support the ideals of democracy. Rather, the design of the digital world presents a dystopian future, with the global reach of “surveillance capitalism” [zuboff2019surveillance] robbing citizens of both power and wealth. The structure of the digital world resembles the “state of nature” (i.e., a social disorder).
In order to establish a self-governed, egalitarian, and just society in the digital world, this article advocates the development of digital social contracts to govern digital human behavior. A digital social contract is the digital counterpart of social contract theories, as envisioned centuries ago by the founding philosophers of the Enlightenment – Thomas Hobbes, John Locke, Jean-Jacques Rousseau, and Pierre-Joseph Proudhon – and more recent thinkers, such as John Rawls [rawls2009theory, rousseau2002social, proudhon2004general, locke2014second, hobbes1914leviathan]. Social contract theories are the cornerstone of modern democracies (they explain the conditions under which people rationally agree to submit their rights to a legitimate authority in return for collective benefits, such as protection, freedom, or justice) yet, thus far, have remained merely an abstract ideal, based on a hypothetical narrative and the presupposition of tacit, rather than explicit, consent [riley2013will]. A digital social contract offers, for the first time in history, a conceptual model to translate the social contract from a hypothetical theory into a political reality, by utilizing technology in the service of the most important ideas of the Enlightenment. In short, a digital social contract is a voluntary agreement between individuals, specified, undertaken, and fulfilled in the digital realm. It allows for conditions to reach the social contract to be programmed by generating equal access to information. It further enables the programming of the method of agreement by implementing a “one person, one vote” system. And it provides the opportunity to check contractual outcomes in ways that comply with requirements of fairness, for instance, by limiting unequal distributional outcomes. We aim for digital social contracts that are equal (in sharing power), just (in allocating resources), and self-governed (among the participating members ). Hence, the equal sharing of power would require mitigating sybils (fake and duplicate identities) and launching digital currencies where distributed and egalitarian coin minting provides a form of Universal Basic Income [van2017basic] to members.
On the technological design, digital social contracts are programs for a distributed, locally-replicated, asynchronous blockchain architecture. Digital social contracts embody the notion of “code-is-law” in that they are a code in a social-contract programming language, which specifies the digital actions parties may take and the terms. Unlike present digital platforms, this code is not inflicted on the user by a monopolistic digital entity to its financial benefit; rather, people who trust each other enter into a code-regulated relationship voluntarily. Digital social contracts allow for cooperative behavior because they disallow faulty, non-cooperative actions; a party can behave only according to the contract. Agents are expected to employ genuine identifiers and function as both actors and validators. An agent may participate simultaneously in multiple social contracts; similarly, each contract may have a different set of agents as parties; the result is a hypergraph with agents as vertices and contracts as hyperedges. Signed indexed transactions (“digital speech acts”), specified and carried out according to a contract, are replicated only among parties to a contract, who ratify them, and are synchronized independently by each agent. A transaction carried out is finalized when ratified by an appropriate supermajority of the parties to the contract. A party to a contract is typically an agent who embodies a natural person via her genuine identifier, but, if deterministic, could also be a synthetic agent (aka “legal person”), which functions algorithmically, very similar to a “smart contract” of standard blockchains [reijers2016governance].
In 2017, Mark Zuckerberg published a vision on how to turn Facebook from a social network to a “Global Community” governing the planet in most aspects of life, where every user can vote on “global problems that span national boundaries” and “participate in collective decision-making” [zuckerberg2017building]. According to Zuckerberg, “Facebook can explore examples of how community governance might work at scale” yet, in his global community, people have no rights and bear no responsibilities; they are a means to make profit for Facebook’s stakeholders. Zuckerberg’s community turns the problem on its head – Facebook is presented as the solution, rather than the problem. The starting point of this article is radically different than Facebook and similar-minded companies in two aspects: 1) vision: it starts from the premise that there can and should a digital public life, complementary to the traditional public life in the physical world, by which political communities govern their life; 2) technology: The only technology that provides sovereignty to its community of users is blockchain. Nobody can unplug Bitcoin or Ethereum; both will keep running as long as someone somewhere keeps running their protocols. Alas, current blockchain technologies are environmentally harmful and plutocratic – they are neither egalitarian nor just as sovereignty is shared not equally but according to one’s wealth, i.e., one’s ability to prove work or stake. We aim to offer an alternative. In summary, digital social contracts are:
Conceptually, a voluntary agreement among individuals, specified, undertaken, and fulfilled in the digital realm.
Mathematically, an abstract model of computation – a transition system specifying concurrent, non-deterministic asynchronous agents engaged in digital speech acts.
Computationally, a program in a Social-Contracts Programming Language with which social contracts among computational agents are easy to express, comprehend and debug.
Technologically, a programmable, distributed, locally-replicated, asynchronous blockchain architecture, operating on mobile phones, tagged by the genuine identifiers of their owners.
Two key concepts are employed in digital social contracts:
Digital Speech Acts: Each party to a digital social contract is equipped with a key pair – a public key and a private key (PKI), with which they can digitally sign text strings and verify each other’s signatures. All that a computational agent can do, as a party to a digital social contract, is perform and perceive digital speech acts, namely sign a digital utterance and send it to the other agents that are parties to the contract, or receive signed digital utterances from these agents.
The Person as an Oracle: Computational agents in a digital social contract face nondeterministic choices: Which room to book, when and where? How much to pay and to whom? How to vote on a proposal to accept a new member to the contract? Computational agents have no volition or free will and hence cannot make such choices on their own. Therefore, nondeterministic choices in the social contract code are interpreted as Oracle calls, where the human operating the computational agent serves as the Oracle. In other words, nondeterministic choices in the code of an agent specify the interactions between the “software” and the “user”, namely between the computational agent and the person operating it: When faced with a nondeterministic choice, the computational agent consults its human operator as to which choice to make.
1.1 Related Work
The concepts and design presented here are reminiscent of the notions of blockchains [blockchainbook], smart contracts [smartcontracts], and their programming languages [solidity]. Hand-in-hand with these we are working on egalitarian currency networks [EgalitarianCurrencyNetworks], an egalitarian and just alternative to existing plutocratic cryptocurrencies such as Bitcoin [bitcoin] and Ethereum [solidity].
A fundamental tenet of our design is that social contracts are made between people who know and trust each other, directly or indirectly via other people that they know and trust. This is in stark contrast to the design of cryptocurrencies and their associated smart contracts, which are made between anonymous and trustless accounts. A challenge cryptocurrencies address is how to achieve consensus in the absence of trust, and their solution is based on proof-of-work [POW] or, more recently, proof-of-stake [POS] protocols. In contrast, social contracts are between known and trustworthy individuals, each expected to posses a genuine (unique and singular) identifier [ggid] (see therein discussion on how this can be ensured). Hence, a different approach can be taken. In our approach, the integrity of the ledger of actions taken by the parties to the social contract is preserved internally, among the parties to the agreement, not between external anonymous “miners”, as in cryptocurrencies. This gives rise to a much simpler approach to fault tolerance, as discussed in the companion paper [ftdsc].
2 Digital Social Contracts
Here we describe a formal model for digital social contracts.
We assume a given finite set of agents , each associated with a genuine (unique and singular) [ggid] identifier, which is also a public key of a key-pair.111We identify the set of agents with the set of parties to the agreement. Extensions will allow an agent to be a party to multiple agreements, and different agreements to have different sets of agents as parties. We expect agents to be realized by computer programs operating on personal devices (e.g. smartphones) of people. Hence, we refer to agents as “it” rather than as he or she.
We identify an agent with its genuine public identifier, and denote by the result of agent signing the string with the private key corresponding to . We assume computational hardness of the public-key system, namely that signatures of an agent with a given identifier cannot be produced without possessing the private key corresponding to this identifier. To avoid notational clutter we do not distinguish between finite mathematical entities and their string representation. Identifying agents with their genuine identifiers makes totally ordered (by the numeric value of the identifier, namely the public key) and hence allows defining tuples and Cartesian products indexed by . If is a tuple indexed by , then we use to refer to the element of . We say that , except for , to mean that the tuple is obtained from by replacing its element by . In particular, if is a sequence, then we say that , except for , to mean that is obtained from by appending to the sequence .
All agents are assumed to be connected via a reliable asynchronous communication network (without assuming a known time limit on message arrival), and require all messages to be authenticated. Informally, the only things an agent can do as a party to a digital social contract are (i) perform a digital speech act [ggid], defined next; (ii) observe digital speech acts performed by others; and (iii) change internal state.222While the formal definition allows a digital speech act to employ an arbitrary string, its intended use is to take meaningful actions. As parties to a social contract employ strings that are meaningful to the other parties, we believe we do not conjure “speech acts” in vain.
A key characteristic of a speech act taken in the physical world is that all people present indeed perceive the person taking the act as well as the act itself. We capture this characteristic by requiring that a digital speech act be (i) digitally signed by the person taking it
Definition 1 (Digital Speech Act, -act).
Given a set of agents , a digital speech act of agent consists of (i) signing an utterance (text string) , resulting in ; and (ii) broadcasting the message to . We refer to a digital speech act by resulting in the signed action as the -act , and let be the set of all -acts for all .
We employ a standard notion of a transition system:
Definition 2 (Transition System).
A transition system consists of a set of states , an initial state , and a set of transitions , , with written as . The set is the outgoing transitions of . A run of is a sequence of transitions from the initial state. A family of transition systems over is a set of transition systems of the form where is a set of transitions over .
A family of transition systems is best thought of as the abstract, syntax-free counterpart of a programming language, where each transition system is the abstract counterpart of a program in the language.
Definition 3 (Implementation).
Assume two transition systems and , and a function , where , referred to as a semantic mapping. Then implements via if:
For every transition , there is a sequence of transitions , , such that and .
For every transition , either or .
can implement if there is a semantic mapping via which implements .∎
Definition 4 (Morphism, Strict).
Given two transition systems and , a semantic function , where is a morphism if implies ; and strict if implies .
That is, in a strict morphism the implementing process provides all the transitions of the implemented process [hesselink1988deadlock].
A strict morphism is an implementation in which every transition of the implementing transition system is mapped to exactly one transition of the implemented transition system, and vice versa. Hence:
A strict morphism among two transition systems is an implementation.
Definition 5 (Compiler).
Given two families of transition systems, , , consider a pair of functions , where is a semantic mapping and is referred to as a compiler. Then implement if for each , implements via . We say that can implement if there is a pair of functions as above that implement .
Eventually, we aim to use the framework developed here to indeed prove that the Social-Contracts Programming Language we are designing implements the abstract transition system of social contracts described herein.
2.2 A Digital Social Contract Transition System
Here we define digital social contracts in the abstract; in particular, we do not address a distributed realization nor agent faults. These issues are addressed in a companion paper [ftdsc].
Remark 1 (Parties, Roles, and Parameterized Social Contracts).
Agents should be able to participate simultaneously in multiple social contracts. Furthermore, a contract may have multiple parties with the exact same role. To address this properly, we should describe digital social contracts as a set of roles, each specified by a parameterized procedure, and bind the formal parameters to actual agent identifiers upon execution of the contract. This is akin to the standard legal practice of using a textual contract template, with role names as parameters (e.g. Landlord, Tenant), and filling in the identities of the parties assuming these roles in an instance of this contract template upon its signature. We defer this distinction between formal and actual parameters in a social contract to avoid notational clutter, and name the parties to the social contract by their genuine identifiers, i.e., their public keys. Later we describe a design for a practical Social-Contracts Programming Language, which will naturally make this distinction.
A digital social contract consists of a set of agents, identified via public keys, and connected via a reliable, asynchronous, order-preserving communication network. Namely, we assume that between any two agents in the network, the network delivers all messages sent from one agent to another – correctly, eventually, and in the order sent.333As agents have public keys with which they sign their sequentially-indexed messages, such a network can be easily realized on an asynchronous network that is not order-preserving and is only intermittently reliable. All that agents can do within a digital social contract is perform digital speech acts (henceforth, acts), which are sequentially-indexed utterances, signed by the agent and sent as messages to all other agents that are parties to the contract, as well as receive such messages. Example acts are “I hereby transfer three blue coins to Sue” and “I hereby confirm the room reservation by Joe”. A digital social contract specifies the digital speech acts each party may take at any state. For example, a social contract regarding the blue currency may specify that I can say that I transfer three blue coins to Sue only in a state in which I in fact have at least three blue coins; and I can say that I confirm Joe’s room reservation only if I have not already confirmed a conflicting reservation.
Our abstract notion of a digital social contract identifies a digital social contract with a transition system. The state of a digital social contract, referred to as a ledger, is composed of the states of each of the agents participating in the contract, referred to as their history, which is but a sequence of digital speech acts. The history of an agent consist of digital speech acts it experienced, in particular: acts by , referred to as -acts, in the order taken, interleaved with acts by the other agents, in the order received from the network. Hence, at any ledger that is a state of the computation, the -acts in the history of agent must be a prefix of the -acts in the history of , for any and . We call such a ledger sound. Next we formalizes this informal description.
We assume a given set of actions . Signing an action by an agent makes the action non-repudiated by . All that an agent that is party to a digital social contract does, then, is perform digital speech acts, as well as receive such acts performed by others, resulting in a sequence of non-repudiated acts - a history of crypto speech acts.
Definition 6 (-act, History).
We refer to , the result of signing an action by agent , as a -act, let denote the set of all -acts by all , and refer to members of as acts. A history is a finite sequence of acts , , , , , . The set of all histories is denoted by .
Next, we define a pair histories to be consistent if they agree on the subsequences signed by each agent.
Definition 7 (Prefix, Consistent Histories).
Given a sequence , a sequence is a prefix of , , if , for some . We apply the notation , of restricting a history to the subsequence of -acts.
Two agent histories are consistent if either or vice versa for every .
A ledger of a digital social contract is an indexed tuple of histories of the parties to the contract. Ledgers are the states of the social contract transition system.
Definition 8 (Ledger).
A ledger is a tuple of histories indexed by the agents , where is referred to as the history of agent in , or as ’s -history.
Following Definition 7, we apply the notation to denote the subsequence of -acts in the -history in .
Our key assumption is that in a ledger that is a state of a computation, each agent’s history is up-to-date about its own acts. Therefore, for agent histories to be consistent with each other, the history of each agent can include at most a prefix (empty, partial or complete) of every other agent’s acts. In particular , the history of cannot include -acts different from the one’s taken by ; nor can it run ahead of and “guess” acts might take in the future.
Note that a ledger is not a linear data structure, like a blockchain, but a tuple of independent agent histories, each of them being a linear sequence of acts. Furthermore, note that , the history of in ledger , contains, of course, all -acts, but it also contains acts by other agents received by via the communication network. Also, note that the -history may be behind on the acts of other agents but is up-to-date, or even can be thought of as the authoritative source in , regarding its own -acts.
Definition 9 (Ledger Diagonal, Sound Ledger).
Given a ledger , the diagonal of , , is defined by for all . A ledger is sound if for every .
As we assume that each agent is up-to-date about its own acts, the diagonal contains the complete sequence of -acts for each agent . Thus, each agent history in a ledger reflects the agent’s “subjective view” of what actions were taken, where the diagonal of a ledger contains the “objective truth” about all agents, as the following observation shows.
If a ledger is sound, then every pair of agent histories in is consistent.
We have defined the states of the transition system, and are now ready to define the transitions themselves.
Definition 10 (Transitions).
The set of social contract transitions consists of all pairs where except for , for some and . The transition is referred to as a -transition, and can also be written as .∎
Definition 11 (Input, Output and Sound Transitions).
A -transition is output if and input if . A transition is sound if it is either input with or output.
If is sound and is sound then is sound.
An Output -transition does not violate soundness as by definition. An Input -transition does not violate soundness thanks to the requirement that . ∎
The next definition aims to capture formally the following two informal requirements:
Output: That an agent may take a -act in state based solely on its own history . In particular, is free to ignore, or to not know, the other agents’ histories in .
Input: That must accept messages from the communication network in any proper order the network chooses to deliver them. In particular, in any state , can accept from any other agent the next consecutive -act not yet in ’s history.
Definition 12 (Closed Set of Transitions).
A set of transitions is:
Output-closed if for any -act , , , and any two output transitions , , if then iff . Namely, if every output -transition is a function of , independently of for all .
Input-closed if contains every sound input transition in .
Closed if it is output-closed and input-closed.
Definition 13 (Digital Social Contract).
A digital social contract among a set of agents is a transition system with ledgers as states , initial state , and a closed set of transitions . The family of all digital social contracts over is denoted by , and is abbreviated as .
We refer to as the family of abstract social contracts, in contrast to its more concrete implementations discussed here and elsewhere. In particular, we view abstract social contracts as specifications for programs in the Social-Contracts Programming Language, discussed next.
This completes the definition of the abstract computational model of digital social contracts. Liveness and fairness requirements for digital social contracts will be discussed in subsequent work.
Note that in the present asynchronous model, neither agent histories nor ledgers have a built-in notion of time. We would like, however, social contracts to be able to have a notion of time and refer to it. Adding time to digital social contracts is an anticipated future extension.
2.3 A Currency Community: Example of a Digital Social Contract
Let be the set of acts. A message corresponds to a payment of 1 coin from to . A transition records in a payment of 1 coin from to . Agent can record a payment from to only if the balance of , according to , is positive.
Formally, let , with . Set , for some , and let . Let denote the closure of in .
The digital social contract over the set of agents specifies a currency community where each agent is granted an initial endowment of coins.
Anticipating the Social Contracts Programming Language defined below, here is an SCPL code defining the role of an agent in this community, with an initial endowment of 10 coins:
Program 1: Currency with an Initial Endowment
agent --> agent(10). agent(Balance), Other(pay(Self)) --> agent(Balance’) where Balance’ := Balance + 1. agent(Balance) --> pay(Other), agent(Balance’) where Balance > 0 & Balance’ := Balance - 1.
Note that the program is nondeterministic in that an agent may choose nondeterministically any
Other to pay to. This notion is discussed at length below.
3 A Social Contracts Programming Language
3.1 An Agent as a State-Transducer
Here we outline the design of a simple social contract programming language. Abstractly, all that an agent can do, as a party to a social contract, is take acts based on its history, and receive acts by others. In a practical social contract, the acts an agent can take typically depend on salient features of its history, rather than on the history in its entirety. For example, I can pay Sue three blue coins depending on whether, according to my entire history, my current balance has at least three blue coins. But, in this case, instead of maintaining my entire transaction history, it is enough that I maintain my balance in order to know whether I can or cannot pay Sue tree blue coins. Similarly, I can confirm Joe’s reservation depending on whether, according to my entire history, I have confirmed a reservation that is still outstanding and conflicts with Joe’s reservation. Similarly, instead of maintaining my entire transaction history, it is enough that I maintain a list of outstanding reservations that I have confirmed in order to know whether I can or cannot confirm Joe’s reservation.
More formally, given that social contracts employ a closed set of transitions, the possible behaviors of an agent can be characterized by a (not necessarily finite and possibly nondeterministic) state transducer. A state transducer reads an input tape (in our case the inputs of an agent ) and writes an output tape (in our case the sequence of -acts), changing its state in the process. The history of an agent fully specifies, even synchronizes, both tapes.
Hence, as an alternative to maintaining entire histories, our programming language endows each agent with an internal state, which can be viewed as a digest of its history. As in a state transducer, the agent’s state may change as a result of an input or an output. Therefore, our proposed Social-Contracts Programming Language (SCPL) presents the program of an agent as a set of rules of the following form:
where is the internal state (state, for short) of prior to taking the transition, is an input -act by some , is an output -act, is the updated state of , and Conditions are any conditions on , , , and , that are required for the transition to take place. The intended meaning of such a rule is that an agent in internal state , upon receiving an act , may take act and change its internal state to , if Conditions are satisfied. Note that degenerate rules, i.e., rules that do not have input and/or output and/or Conditions are allowed.
In general, a programming language aims to provide a finite description to infinitely many computations; in particular, we wish our social contracts programs to describe potentially infinitely-many social contract transitions. To do so, our programming language rules must be parameterized, namely must have variables. SCPL incorporates logic variables and compound terms, very much in the style of logic and concurrent logic programming languages. Next we defined the syntax of SCPL; its operational semantics via a transition system; and show that SCPL transition systems implements.
3.2 SCPL Programs: Syntax with Examples
A programming language needs a mechanism for binding parameters to values. We follow concurrent logic programming languages in using matching (one-way unification) for parameter passing, and logic terms for structured data types.
Definition 14 (SCPL Syntax).
These are the syntactic building blocks of SCPL programs:
The set v of variable names (variables, for short) consists of all alphanumeric strings beginning with an uppercase letter, e.g. X, X1, Xs, and Foo, as well as alphanumeric strings beginning with underscore , e.g. boy; an underscore “” on its own is referred to as an anonymous variable, and is a shorthand for a unique variable name not occurring anywhere else.
The set of constant names (names, for short) consists of all alphanumeric strings beginning with a lowercase letter, e.g. a, a1, and foo, as well as quoted strings, e.g. “,”.
The set of numbers consists of all numeric strings, which may include a decimal point, e.g. 0, 1, 103.65.
The set t of terms consists of all variables, numbers, and n-ary terms of the form , ,where is a name, referred to as the functor of , and each is a term, , referred to as a subterm of .
By convention the constant name  (read “nil”) represents an empty list, the binary term represents a list with the first element and rest , the term is a shorthand for the singleton list and the term is a shorthand for the nested term
Note that there are infinitely many lists, and in general infinitely many terms.
The set of social contract rules consists of all terms of the form
(the full syntax of the output rule being .) Here is an examples of an output rule and an input rule:
tourist(roaming) --> reserve(Host), tourist(waiting(Host)). tourist(waiting(Host), Host(reservation_confirmed(Self)) --> tourist(lodging(Host)).
In such rules, , referred to as the pre-state, , referred to as the post-state, and , referred to as the output act of the rule are any terms, and , referred to as the input act of the rule, is a unary term of the form for some name and some term . For programming convenience, we also provide for combined rules:
Here is an example of a combined rule:
host(free), Tourist(reserve(Self))) --> reservation_confirmed(Tourist), host(reserved(Tourist)).
Such a rule is a shorthand for the input rule and the output rule , where the intermediate state contains all variables shared between the left-hand and right-hand sides of the rule and has as a functor a new constant name that does not occur in the program. For example, the general rule above is a shorthand for the following two rules:
host(free), Tourist(reserve(Self))) --> x(Tourist). x(Tourist) --> reservation_confirmed(Tourist), host(reserved(Tourist)).
xis a name not occurring anywhere else in the program.∎
As the output transitions of a social contract transition system depend only on the history the agent taking the transition, we wish to preserve this property in the programming language. The following notions are instrumental in ensuring that.
Definition 15 (Ground Term).
A term occurs in term , denoted , if or if is an -ary term for some constant and occurs in for some . A term is ground if it no variable occurs in it, namely for every variable name . The set of ground terms is denoted by .
Definition 16 (Explicit Nondeterminism).
A set of social contract rules satisfies explicit nondeterminism if for every two ground instances of rules in with the same pre-state and with post-states and , if then the two rules are not degenerate and have two different acts.
Here are examples of pair of rules violating explicit nondeterminism.
tourist(roaming) --> reserve(Host), tourist(waiting(Host)). tourist(roaming) --> reserve(Host), tourist(lets_try_another(Host)). tourist(waiting(Host1,Host2), Host1(reservation_confirmed(Self)) --> tourist(lodging(Host1)). tourist(waiting(Host1,Host2), Host1(reservation_confirmed(Self)) --> tourist(waiting(Host2)). host(free) --> tourist. host(free), Tourist(reserve(Self))) --> host(confirm_reservation(Tourist)).
While program rules have in general infinitely many instances, a program can be determined to be explicitly nondeterministic effectively using the following observation:
Observation 4 (Conditions for Explicit Nondeterminism).
Let be a set of SCPL rules. Then has explicit deterministic iff it has no two rules with pre-states and , post-states , and acts and such that:
If the there are two rules violating the right-hand side of the “iff” then instantiate and differently thus providing a counterexample to explicit nondeterminism. If there is a counterexample to explicit nondeterminism, then the two rules of which the counterexample is an instance also provide a counterexample to the right-hand side, as the two rule instances determine a unifier for which and are not identical. ∎
Definition 17 (SCPL Role, Program).
A social contract role program is a list of social contract rules with initial states having the same functor, referred to as a role name (role, for short), one of which having a 0-ary pre-state. An SCPL programs is a pair , where is a set of explicitly-nondeterministic social contract role programs and , referred to as the activation of , is a list of pairs , where is an agent’s name and is term with its functor being a role name in . The set of agent names in is denoted by , and denotes the set of all social contract programs.
Remark 3 (Pragmatics).
The syntax of role programs employs the following defaults and abbreviations:
Selfis a reserved variable name, bound to the name of the agent occupying the role.
A -act is signed by implicitly, so the output act is perceived by all agents as the signed act
Input acts that have no rules for handling them are ignored, namely received without changing the agent’s state. Typically, these would be acts relevant to other agents.
3.3 An Online Lodging Marketplace
Here we present a distributed social contract among tourists and hosts. It is highly simplified, just to illustrate the concept:
There is a bunch of tourists and a bunch of hosts; initially all hosts are free.
A tourist may request a room from a host and wait; if the room is free, then the host grants the request and records the room as booked; if the room is booked, then the host denies the request.
If the request is granted, then the tourist checks in, and then checks out; when the tourist checks out, the host records that the room is free. If the request is denied, then the tourist may request a room again, from the same host or from another host.
No money exchange here.
First, the host:
The state of the host can be either
reserved(Tourist). If an
free host received a
reserve(Self,Tourist) request, it grants it, by stating
granted(Tourist) and changing its state to
reserved(Tourist). When the tourist that reserved the room checks out, the booked owner becomes
The following are SCPL roles for a simple-minded Airbnb-less social contract among hosts and tourists.
First, an example of a
host role program:
Program 2: Host Role
host --> host(free). host(free), Tourist(reserve(Self))) --> reservation_confirmed(Tourist), host(reserved(Tourist)). host(reserved(Tourist), Tourist1(reserve(Self))) --> reservation_denied(Tourist1), host(reserved(Tourist)) where Tourist =\= Tourist1. host(reserved(Tourist)), Tourist(checkout(Self)) --> host(free).
Now, the tourist:
The state of the tourist can be either
waiting for a response to a reserve request,
The following is an example of a
tourist role program:
Program 3: Tourist Role
tourist --> tourist(roaming). tourist(roaming) --> reserve(Host), tourist(waiting(Host)). tourist(waiting(Host), Host(reservation_confirmed(Self)) --> tourist(lodging(Host)). tourist(waiting(Host)), Host(reservation_denied(Self)) --> tourist(roaming). tourist(lodging(Host)) --> checkout(Host), tourist(roaming).
Here are the rules for a tourist :
The first rule is an output rule, missing an incoming message , so this rule can apply whenever the agent’s state is . Note that a
tourist nondeterministically chooses a room owner to reserve a room from. In our interpretation, this nondeterminism is realized as a query to the person operating this agent, which room would you like to reserve? If and when the person chooses from which
Host to reserve, the agent then requests to reserve the room, sending the message
reserve(Host). The agent then waits for the response. If the reservation is
reservation_confirmed it checks in at its leisure. If the request is
reservation_denied, it may choose again a host to reserve from.
The role programs as written can accommodate multiple tourists and multiple hosts in the same social contract. Here is an example of an activation of a social contract with these two roles:
Program 4: Activation of a Tourists/Hosts Social Contract
Here is a possible history of executing this social contract thus activated:444This is actually a trace of a Concurrent Prolog program hand-compiled from this social contract. The trace include also the “Oracle choices” of the various agents.
H / 1 = gal(oracle(reserve(ouri))) H / 2 = udi(oracle(reserve(nimrod))) H / 3 = avigail(oracle(reserve(nimrod))) H / 4 = udi(reserve(nimrod)) H / 5 = gal(reserve(ouri)) H / 6 = nimrod(reservation_confirmed(udi)) H / 7 = avigail(reserve(nimrod)) H / 8 = nimrod(reservation_denied(avigail)) H / 9 = ouri(reservation_confirmed(gal))
We now consider a different social contract, where a broker that accumulates a list of reservations and a list of free rooms, assuming all rooms are equivalent, and grants reservations on a first-come-first-served basis.
Program 5: Brokered Hosts/Tourists Social Contract
host --> host(free) host(free) --> free, host(waiting). host(waiting), broker(reservation(Tourist,Self)) --> host(reserved(Tourist)). host(reserved(Tourist)), checkout(Tourist,Self) --> host(free). tourist --> tourist(roaming). tourist(roaming), reserve --> tourist(waiting). tourist(waiting), broker(reservation(Self,Host)) --> tourist(lodging(Host)). tourist(loading(Host)) --> checkout(Host), tourist(roaming). broker --> broker(,). broker(Rooms,Reservations), Host(free) --> broker(Rooms’,Reservations) where Rooms’ is the result of appending Host to Rooms. broker(Rooms,Reservations), Tourist(reserve) --> broker(Rooms,Reservations’) where Reservations’ is the result of appending Tourist to Reservations. broker([Host|Rooms],[Tourist|Reservations]) --> reservation(Tourist,Host)), broker(Rooms,Reservations)
This is not far from how Airbnb essentially operates. With a broker, one may have two separate social contracts. One among room owners and the broker (Airnbn), and one among the tourists and the broker (Airnbn again). The broker, then, is a party to both social contracts. The broker may receive a confirmation signed by the room owner via the social contract of the owners, and forward it to the tourist, via the tourists social contract. Such a signed confirmation is non-repudiated, even if obtained indirectly. Third, one may add payments, as in real life. Realizing a currency network using digital social contracts is described in a companion paper [EgalitarianCurrencyNetworks]. However, in our realization, the broker need not collect rent from transactions among the tourists and the room owners, as Airbnb does. It could be owned and operated cooperatively by the tourists, by the owners, or by both. The issue of shared, autonomous agents (aka smart contracts) will be discussed in detail in a subsequent paper. Also, in this paper we have eschewed the programming language design issue of how to bind formal parameters to actual parameters in a social contract, parameter scope, and how to start a social contract. These are standard issues of programming language design, but fixing these details in this high-level paper is premature. The following muck-up code, without formal semantics yet, may illustrate a design option, assuming all names stand for public keys, for which the private keys are known by the respective agents.
3.4 A Egalitarian Currency
As another example, consider an egalitarian currency [EgalitarianCurrencyNetworks]. The social contract assumes a clock agent that issues clock ticks. Each party to the social contract may mint one coin at each clock tick, may receive payments from other agents, and may pay other agents if its balance affords the payment.
Program 6: Egalitarian Currency
agent --> agent(0). agent(Balance), clock(tick) --> agent(Balance’) where Balance’ := Balance + 1. agent(Balance), Other(pay(Self,X)) --> agent(Balance’) where Balance’ := Balance + X. agent(Balance) --> pay(Other,X), agent(Balance’) where Balance >= X & Balance’ := Balance - X.
Note that in the last rule of Of course, a person may operate computational agents, possibly endowed with Artificial Intelligence, that undertake volitional acts on her behalf; investigating this direction is beyond the scope of this paper.
agent, both the addressee of the payment,
Other, and the amount
X, are free variables, to be determined by volition of the payer.
Host to reserve from, is a free variable in the
Tourist program, to be determined by volition of the tourist. As discussed above, the intention is that in the implementation of the Social Contracts Programming Language, a computational agent will take volitional acts at the advice of the person operating the agent.555
Of course, a person may operate computational agents, possibly endowed with Artificial Intelligence, that undertake volitional acts on her behalf; investigating this direction is beyond the scope of this paper.An exception may be a clock agent, which will use a physical clock (or in any case an outside computational agent connected, indirectly, to a physical clock) to decide when to tick. Formally, and in the implementation of the Social Contracts Programming Language, we view the external agent as an Oracle that resolves explicit output nondeterministic choices enabled by the contract.
3.5 A Simple Data Storage Service
A similar example of rental goods is a distributed data storage (cloud) service. Here is a simplified setting:
There are a bunch of users and a bunch of data storage owners; initially all storage spaces are free.
A user may request some storage space (to store his data) from an owner and wait; if some space is free, then the owner grants the request, possibly partially, and records the granted space as booked; if the space is booked, then the owner denies the request.
If the request is granted, then the user stores her data, and then checks out; when the user checks out, the owner records that the space is free. If the request is denied, then the user may request a space again, from the same owner or from another owner.
No money exchange here.
The social contract for this setting is similar to the unbrokered hosts/tourists setting, with the addition that a reservation requests capacity, and can be satisfied fully or partially. In the brokered setting, there is an added complication that requests can be satisfied in fractions, so leftover storage factions for both users and hosts should be managed.
3.6 Citizens Band and Social Community Examples
Here we consider dynamically growing a social contract, in a simple “Citizens Band” (CB) application, where anyone can talk, everyone hears what everyone else says, and anyone may invite anyone to join.
Program 7: Citizens Band
agent --> say(X), agent. agent --> Friend#agent, agent. agent, Foo(hi_there) --> welcome(Foo), agent.
We now show the social contract of a social community with managers and members. Only a manager can add members or turn members to managers.
Program 8: WhatsApp-like Group with a Manager
manager --> manager(). manager(Members) --> Friend#member, manager([Friend|Members]). manager(Members) --> please_leave(Member), manager(Members’) where Members’ is a result of removing Member from Members. manager() --> stop. member --> says(X), member. member, _(please_leave(Self)) --> says(bye), stop. member --> says(bye), stop.
3.7 Egalitarian Governance of Social Contracts
The examples up to this point allow agents to realize sovereignty, transparency, and privacy over a shared medium of interaction. Here we consider the standard principle of democracy, generally abbreviated as “one person, one vote”. That is, we show how a community may form democratically. This method of democratic community formation could be applied to any of the social contracts mentioned above - the Social Community, Hosts and Tourists, and Egalitarian Currency. Here decisions to add or remove a member are taken by a simple majority, but extending the contract to require a supermajority for taking a decision is not difficult.
The democratic community has a secretary that handles the ballot. The secretary is deterministic, and as such does not need an Oracle. Hence, it is autonomous and not bound to any specific individual. It is initiated by the founder.
Program 9: Democratic WhatsApp-like Group
founder --> autonomous#secretary([Self]), member. secretary --> secretary(). secretary(Members), _(propose(X)) --> ballot(X,Members,0), secretary(Members). secretary(Members), ballot(X,,Result) --> secretary_apply(X,Result,Members). secretary_apply(X,Result,Members) :- secretary(Members) where Result =< 0. secretary_apply(add(Member),Result,Members) :- Member#member, secretary([Member|Members]) where Result > 0. secretary_apply(remove(Member),Result,Members) :- please_leave(Member), secretary(Members’) where Result > 0, Members’ is the result of removing Member from Members. member --> says(X), member. member, ballot(X,[Self|Members],R) --> ballot(X,Members,R’), member where R’ := R, R+1, or R-1. member, _(please_leave(Self)) --> says(bye), stop. member --> says(bye), stop.
Note that this is a very simple program, in particular as (1) there is no option to decline an invitation (2) agents must wait for other agents to vote. Indeed, we provide the program mainly as a proof of concept, but to implement a practical democratic decision process, more complex program is needed. We also note that votes are public to the community members and are not anonymous.
4 Operational Semantics of SCPL
The operational semantics of SCPL is given by mapping every SCPL program into a transition system (for Social Contract with a Distributed State). We first define the model, then show how SCPL programs are mapped into SCDS transition systems, and finally show that SCDS implement SC.
We assume three given sets: of agents, of agent actions, of agent states.
Definition 18 (Transition Function).
We assume transition function , where is referred to as an output transition if and input transition if . An input transition is always defined, namely different from : for every , , and .
Definition 19 (Addressed Message Store).
A set is referred to as an addressed message store. A -act is sent to through by adding to , and is received by removing it from .
Remark 4 (Signed Messages, Ordered Messages).
A message in the message store indicates that some ha sent the message to , and has not received it yet. Recall that the agent signs the message , so, even though we store objects of the form , where is the destination and is the message, the original sender is implicitly there as well, as the signatory of . Furthermore, peer-to-peer messages need to be processed by the recipient in the order sent. To achieve that, we could number actions sequentially and order them upon receipt. Instead, we simply assume that the message store delivers point-to-point messages in the order sent. We relax this assumption in a companion paper, when discussing fault-tolerant implementations [ftdsc].
Definition 20 (Distributed State Configurations).
The set of SCDS configurations consists of all pairs where is agents’ state and is a message store.
Definition 21 (SCDS transitions).
The set of SCDS transitions over consist of all pairs , where , , except for , , and either:
Output: , .
Input: , and .
In which case the transition is referred to as an output -transition and can also be written as , or input -transition and can also be written as , respectively.∎
Definition 22 (SCDS Transition System).
An SCDS transition system has configurations and transitions defined via agents , actions , and a transition function , to be .
Proposition 1 (History Determines State).
In an run, the history of an agent uniquely determines its state.
By induction on history length. The initial state of every agent is uniquely determined by . Thanks to , current agent state is mapped by the next action to a unique agent state. ∎
We specify now the configurations and transition function for an SCPL program : The set of actions is the set of all ground terms, , the set of agents is and the set of agent’s states is the set of all ground terms .
Definition 23 (Distributed State Corresponding to a Program).
Given an SCPL program , the corresponding set of SCDS configurations consists of all pairs where is agents’ state and is a message store, and the initial state determined by .
We now derive SCDS transitions from SCPL programs. Each SCPL rule with variables stands for infinitely-many SCDS transitions, one for each instance of the rule, as defined next. Recall that a substitution is a mapping from variables to terms; for any substitution and term , denote by the result of replacing every variable by , and refer to as an instance of ; and as a ground instance of if is ground.
Definition 24 (Grounded Program).
Given a program , we define its grounded roles in several steps, as follows:
Signatures: Modify every output rule in by adding
Self(_)to the output action. For example, the first clause of the
touristrole above becomes:
tourist(roaming) --> Self(reserve(Host)), tourist(waiting(Host)).
Ground Instances: Let the set of grounded rules include all ground instances of any input rule and output rule . An example ground instance of the rule above is:
tourist(roaming) --> luca(reserve(nimrod)), tourist(waiting(nimrod)).
Closure for Inputs: Add to all ground input rules for which has no ground rule , where .
Note that since the set of terms is infinite, if is not ground then is infinite.
Definition 25 (SCPL transition function).
With each program we associate a state-transition function , defined for every , , and as follows:
if , otherwise.
The transition function is well-defined.
Thanks to explicit output-nondeterminism, case 1 is unique if defined. Thanks to input-determinism and input closure, case 2 is well defined. ∎
Definition 26 (SCDS transitions Corresponding to a Program).
Given an SCPL program , the set of corresponding SCDS transitions over consist of all pairs , where , , except for , , and either:
Output: , .
Input: , and .
In which case the transition is referred to as an output -transition and can also be written as , or input -transition and can also be written as , respectively.∎
Definition 27 (SCDS Transition System Corresponding to a Program).
Given an SCPL program , its corresponding transition system has configurations as states and transitions . The family of SCLP transitions systems is denoted by .
We show that implements by describing a compiler that takes an abstract SC transition system and returns a state-based distributed transition system SCDS that implements SC. It does so by first compiling SC to an SCPL program, and then map the program to its operational semantics SCDS. We gain here not only the understanding that SCDS indeed implements SC, but also the sense in which social contracts described via SC are in fact specifications for SCPL programs.
Definition 28 (Compiling SC to SCDS).
We define as follows. Given an transition system , we first map it to the grounded SCPL program where and for every :
We then define .
We note in passing that could be, in principle, infinite. However, if bisimilarity induces a finite number of equivalence classes on , then instead of the post-state of a transition being , it could be a short representative of the equivalence class of , and by looping thus, could also be finite.
AtoD is a compiler.
To prove this proposition, we have to show that implements , and to do so we have to show a mapping from states to states and prove it to be an implementation of by . Recall that for SC output -transitions, the closure condition ensures that the history of is sufficient to determine what transitions can take, and under the AtoD compiler, this history is indeed encoded in ’s state . For SC input transitions, what matters is the difference between the history of , , and the diagonal , and a sound input transition can only take as input an action of some other agent that is next in difference between the -acts in the history of , , and the diagonal . Hence, we show that in computations, the message store captures precisely the difference between the diagonal and the histories of agents, and therefore provides a sound basis for sound input transitions.
Observation 6 (State determines Message Store).
Let SC be a social contract and . Consider a computation , where . Then contains exactly all messages , such that , for all .
We prove by induction and a simple case analysis. The claim holds vacuously for . Assume it holds for and consider . There are two cases:
Input: , in which case following the transition, the message is removed from and added to , preserving the inductive assumption.
Output: , in which case following the transition, the message is added to and added , preserving the inductive assumption.
First we note that with this compiler, and (up to syntactic variations). Consider the mapping , where . Namely, the mapping ignores the messages store. We claim that is a strict morphism. In an output transitions, the state of each agent is precisely its history, so there is no difference between and in that regard, and hence. Regarding input transitions, as noted in Observation 6, the message store captures precisely the difference between the ledger and the diagonal, and therefore each SDSC transition corresponds precisely to an SC transition under . In other words, is a strict morphism. ∎
The compiler constitutes a constructive proof. ∎
We have introduced the concept of digital social contracts, provided a mathematical definition of them, outlined a design for a social contracts programming language, and demonstrated its social utility via program examples. Much remains to be done; some is discussed in companion papers [ftdsc, EgalitarianCurrencyNetworks].
Ehud Shapiro is the Incumbent of The Harry Weinrebe Professorial Chair of Computer Science and Biology. We thank the generous support of the Braginsky Center for the Interface between Science and the Humanities. Nimrod Talmon was supported by the Israel Science Foundation (ISF; Grant No. 630/19).