# UpEnd - A Conceptual Tutorial UpEnd is not a traditional database - at its core, there are no tables, objects, or files. An entire UpEnd **Vault** is a flat list of **entries**. An **entry** is a single "statement" that's true within the system. The core of an entry is an _Entity/Attribute/Value triplet_. For example: | Entity | Attribute | Value | | ----------------------- | ------------- | --------------- | | John | Age | 23 | | Prague | Is In Country | Czech Republic | | (hash of) `track01.mp3` | Artist | Various Artists | | https://upend.dev | Title | UpEnd | Formally speaking: - **Entity** is the thing the statement is about. It can be one of the following: - **Hash**, typically of a file, but also possibly of another **entry**. - [**UUID**](https://en.wikipedia.org/wiki/Universally_unique_identifier), for arbitrary objects that exist solely within UpEnd (groups/tags, annotations, etc.) - **URL**, anything that exists on the web. - **Attribute**, for data that belong to UpEnd's attributes (such as their different names, etc.). - **Attribute** is the "kind" of a statement. - It can be any text string, but there are some "reserved" attributes by UpEnd by default. - **Value** is the actual "fact" you're stating. It can be one of the following: - A text string - A number - An address of an **entity**. (Each **entry** also has a _timestamp_, denoting when it was added, and _provenance_, i.e. the origin of this entry - whether it was added by an automatic process or a user. A full example of an **entry** therefore would be `John / Age / 23 / 2023-05-01 19:20:00 / API IMPORT`) All other concepts within UpEnd arise as a consequence of combinations of **entries**. **Objects** emerge as multiple **entries** with the same **entities** accrue. In other words, an **object** is a collection of entries pointing to the same **entity**. A file object therefore may look something like: | Entity | Attribute | Value | | ----------------------- | --------- | ---------------- | | (hash of) `photo01.jpg` | Author | John Doe | | (hash of) `photo01.jpg` | Label | photo01.jpg | | (hash of) `photo01.jpg` | Label | Birthday 001.jpg | | (hash of) `photo01.jpg` | Taken at | 2020-04-01 | | (hash of) `photo01.jpg` | ... | ... | (In the UI, the **Entity** part of entry listings is often left out, as it's redundant and implied by the object view.) However, while a file object has an obvious **entity** to point to, a _Tag_ or a folder has no inherent identity of its own, and therefore no hash. This is the purpose of [_UUIDs_](https://en.wikipedia.org/wiki/Universally_unique_identifier). A _UUID_ is randomly generated for every object as needed. A **Group** is a equivalent of a folder or a tag. Its purpose is to serve as a collection of related items. It is a "conventional" object - there is nothing about UpEnd that necessitates **Groups** to exist, but since it provides a very useful abstraction, there is built-in functionality that works with **Groups**, as well as affordances in the UI. It looks like this: | Entity | Attribute | Value | | --------------------------------------------- | --------- | ----------------------- | | `f9305ca5-eabd-4a97-9aa4-37036d2a6ca4` (UUID) | Label | Birthday Photos | | `f9305ca5-eabd-4a97-9aa4-37036d2a6ca4` (UUID) | Contains | (hash of) `photo01.jpg` | >Issue `CONTENT UNADDRESSABLE` >This means that while the **vaults** of various users will refer to the same files by the same **Entity** addresses - because a file is uniquely identified by its hash - this does not apply to any other objects such as **Groups**, as they are identified by a _UUID_, which is random. If two **vaults** were therefore combined, **entries** referring to the same files would "add up" correctly, and your existing **entries** about given files would be complemented by the **entries** of the other **vault**, but any **groups** would potentially be duplicated. >This is an inherent problem, and cannot be easily solved; if everything were content-addressed, including **groups**, any single change (such as adding or removing a file from a **group**) would ripple throughout the entire system, as other related **entries** would have to update their **entities** or **values** to match this new address, which would change their content, and therefore their hash, and so on. Furthermore, this would also mean that no two folders (or **groups**) could ever share names, for example, as their content would at one point be identical, and therefore their identity as well. UUIDs provide a way for two otherwise identical **objects** to coexist. >Not all is lost, though - two vaults can still combine in a meaningful way allowing mutual understanding - but it does necessitate an explicit mechanism resolving the semantics of combining _UUID_ referred objects such as **groups** (in other words, a separate addressing scheme). For example, if it's desirable that no matter what vault you happen to be in, the `music` **group** is always the same (and thus two users categorizing their favorite articles in the `music` group can see each other's articles) a convention can be established that all "universal" **groups** also receive an entry with a `Universal Key` **attribute**, which is then used to tell which **groups** are supposed to be the same across different vaults - and which are, for example, just a `music` group someone happened to create to categorize their favorite songs. >Notably, this issue is completely moot unless you happen to compare different **vaults**. If all you're concerned with is a single **vault** on your computer, you don't need to worry at all about *UUID* objects.