# SDK: files and storage

> The types of the file API: handed-over files, shares, folder pages, jobs, the recycle bin, versions and storage requests.

Source: https://pithyx.org/docs/reference/sdk/files/
Markdown: https://pithyx.org/docs/reference/sdk/files.md

The methods are on `app.files`, `app.trash` and `app.jobs` (see [app and connection](https://pithyx.org/docs/reference/sdk/app/)); this page has the types they take and return. Paths are relative to a location with `/` as separator; an app never sees a path on the host.

Generated from the TSDoc comments of @pithyx/sdk 1.0.0-rc.9 at build time; the text below the headings is the comment in the source.

## Interfaces

### ShareLocation

A share from `files.shares`, the only location the versions and the recycle bin take: a storage request is a folder
inside a share, without snapshots or a bin of its own.

#### Properties

##### share

```ts
share: string;
```

The `id` of a share from `files.shares`.

---

### FileEntry

One entry of a folder.

#### Properties

##### name

```ts
name: string;
```

Name within its folder.

##### kind

```ts
kind: FileKind;
```

What the entry is.

##### size

```ts
size: number;
```

Bytes for files, 0 for folders.

##### modified

```ts
modified: string;
```

Last change of the content, ISO 8601 UTC.

---

### ShareInfo

A share the user can use, with the user's own access.

#### Properties

##### id

```ts
id: string;
```

Stable id, used as `{ share: id }`.

##### name

```ts
name: string;
```

Name shown to users.

##### access

```ts
access: 'read' | 'readWrite';
```

The user's access: `read`, or `readWrite` to change files.

##### unavailable?

```ts
optional unavailable?: "poolMissing" | "poolUnavailable" | "notMounted";
```

Set while the share's files cannot be reached: `poolMissing` (its disks are not connected), `poolUnavailable` (its
pool stopped because disks are missing) or `notMounted`. Calls on it fail with [`fs.share.unavailable`](https://pithyx.org/docs/reference/errors/#fs.share.unavailable) until the
share is back, which `sharesChanged` announces.

##### kind?

```ts
optional kind?: "home" | "userHome";
```

Set for a home instead of a shared folder: `home` is the user's own (named `home`), `userHome` another user's home
(named after its folder), which only the core apps of administrators see. Left out for a shared folder.

---

### FolderPage

One page of a folder.

#### Properties

##### path

```ts
path: string;
```

The folder, relative to its location ("" for the root).

##### folderId

```ts
folderId: string;
```

Stable id of the folder, also after a rename.

##### total

```ts
total: number;
```

Entries in the folder when the page was read.

##### entries

```ts
entries: FileEntry[];
```

This page, in the requested order.

##### nextCursor

```ts
nextCursor: string | null;
```

Pass as `cursor` for the next page; null on the last page. The cursor stays valid while the folder changes.

---

### FileSelection

A selection in one folder.

#### Properties

##### location

```ts
location: FileLocation;
```

Where the folder is: a share, or a storage request of the manifest.

##### folder

```ts
folder: string;
```

The folder the names are in.

##### items

```ts
items: FileItems;
```

The entries of the folder that are meant.

---

### FileOperation

A copy, move or delete that runs as a job.

#### Properties

##### kind

```ts
kind: 'copy' | 'move' | 'delete';
```

What to do. A move within one file system is a rename; across file systems it copies, then deletes.

##### source

```ts
source: FileSelection;
```

The entries to work on, all in one folder.

##### target?

```ts
optional target?: object;
```

The folder to copy or move into. Required for copy and move, not allowed for delete.

###### location

```ts
location: FileLocation;
```

Where the target folder is: a share, or a storage request of the manifest.

###### path

```ts
path: string;
```

The target folder, relative to its location.

##### onConflict?

```ts
optional onConflict?: ConflictPolicy;
```

For copy and move; `fail` when left out.

##### permanent?

```ts
optional permanent?: boolean;
```

For delete: remove for good instead of moving to the share's recycle bin. Set it only when the user explicitly
asked for it.

---

### JobInfo

A long operation of the user, and its progress.

#### Properties

##### id

```ts
id: number;
```

Id for `jobs.cancel` and in `jobChanged` events.

##### kind

```ts
kind: string;
```

For example `files.copy`, `files.trash`, `files.restore`.

##### state

```ts
state: JobState;
```

Where the job is.

##### progress

```ts
progress: object;
```

Entries and bytes done and in total; totals grow while a job still counts what it works on.

###### itemsDone

```ts
itemsDone: number;
```

Entries finished.

###### itemsTotal

```ts
itemsTotal: number;
```

Entries counted so far.

###### bytesDone

```ts
bytesDone: number;
```

Bytes copied or moved.

###### bytesTotal

```ts
bytesTotal: number;
```

Bytes counted so far.

###### current

```ts
current: string | null;
```

The entry being worked on, relative to its location.

##### problem

```ts
problem: Problem | null;
```

Why the job failed, with the stable code and its params.

##### result

```ts
result:
  | {
  done: number;
  skipped: string[];
}
  | null;
```

When it finished: entries done and paths left out (conflicts with `skip`, symlinks, which are never copied).

###### Union Members

###### Type Literal

```ts
{
  done: number;
  skipped: string[];
}
```

###### done

```ts
done: number;
```

Entries the job finished.

###### skipped

```ts
skipped: string[];
```

Paths it left out.

---

`null`

---

### TrashEntry

An item in a share's recycle bin.

#### Properties

##### id

```ts
id: number;
```

Id for restoring or deleting it for good.

##### name

```ts
name: string;
```

Its name when it was deleted.

##### originalPath

```ts
originalPath: string;
```

Where it was, relative to the share; restoring puts it back there.

##### kind

```ts
kind: FileKind;
```

What it was.

##### size

```ts
size: number;
```

Bytes, for a folder everything inside it.

##### deletedAt

```ts
deletedAt: string;
```

When it was deleted, ISO 8601 UTC.

##### deletedBy

```ts
deletedBy: string | null;
```

User name of who deleted it, if that user still exists.

##### expiresAt

```ts
expiresAt: string | null;
```

When it is deleted for good, or null when the share keeps items until the bin is emptied.

---

### TrashPage

One page of a recycle bin, newest first.

#### Properties

##### items

```ts
items: TrashEntry[];
```

This page of the bin.

##### nextCursor

```ts
nextCursor: string | null;
```

Pass as `cursor` for the next page; null on the last page.

##### retentionDays

```ts
retentionDays: number;
```

Days the share keeps deleted items; 0 keeps them until the bin is emptied.

---

### FileVersion

An earlier version of a file or folder, from a snapshot of the share's dataset.

#### Properties

##### snapshot

```ts
snapshot: string;
```

The snapshot it is in; pass it to `files.restoreVersion`.

##### createdAt

```ts
createdAt: string;
```

When the snapshot was taken, ISO 8601 UTC.

##### kind

```ts
kind: FileKind;
```

File or folder.

##### size

```ts
size: number;
```

Bytes for files, 0 for folders.

##### modified

```ts
modified: string;
```

Last change of the content in that version, ISO 8601 UTC.

---

### FolderChange

Changes of a watched folder since the last event.

#### Properties

##### watch

```ts
watch: string;
```

The id `files.watch` returned.

##### changed

```ts
changed: FileEntry[];
```

Entries that appeared or changed, with their current metadata.

##### removed

```ts
removed: string[];
```

Names that are gone.

##### resync

```ts
resync: boolean;
```

Changes were lost (the kernel queue overflowed): list the folder again.

##### gone

```ts
gone: boolean;
```

The folder itself was deleted or moved away; no more events come for this watch.

---

### UploadProgress

Progress of an upload started with an `upload` id.

#### Properties

##### upload

```ts
upload: string;
```

The id given to `files.upload`.

##### loaded

```ts
loaded: number;
```

Bytes sent so far.

##### total

```ts
total: number;
```

Size of the file in bytes.

---

### StorageRequest

A place for files the app needs, declared by name and shown to the administrator with its `name`, for example "Photo library". At install an administrator maps it to a folder in a shared folder (and can change that later). The app only ever sees the name and paths inside it: the window reaches it through the SDK file API as `{ storage: id }`, the backend services listed in `services` find it as the Compose volume named `id`. Users reach it with their own rights on the mapped folder, never with more than `access`.

#### Properties

##### id

```ts
id: string;
```

Unique within the app.

##### name

```ts
name: LocalizedName;
```

##### description?

```ts
optional description?: LocalizedText;
```

##### access

```ts
access: 'read' | 'readWrite';
```

The most the app may do with the mapped folder: `read` or `readWrite`. Users never get more than their own rights on the folder, and with `read` every backend service mounts it read-only.

##### required

```ts
required: boolean;
```

The app cannot start until this storage is mapped.

##### services?

```ts
optional services?: string[];
```

Backend services that mount this storage. Needs a `backend`.

###### Min Items

1

---

### FileHandler

Files the app can open. The desktop offers the app in "Open with" only for these types and sends it only such files (`launch`, `openFile`). An extension belongs to one handler only.

#### Properties

##### extensions

```ts
extensions: string[];
```

Lowercase extensions without the leading dot, for example `png` or `tar.gz`.

###### Min Items

1

###### Max Items

32

##### mimeTypes?

```ts
optional mimeTypes?: string[];
```

MIME types, for example `image/png`.

###### Min Items

1

###### Max Items

32

##### isDefault?

```ts
optional isDefault?: boolean;
```

Whether the app is the default for these files when it is the only handler.

---

### FileRef

A file the user handed to the app (opened with it, or picked in a desktop dialog). The app never learns where the
file is: `ref` is an opaque handle, valid for this user and app, that only the SDK file API accepts.

#### Properties

##### ref

```ts
ref: string;
```

Opaque handle; only the SDK file API accepts it.

##### name

```ts
name: string;
```

File name with extension, for display.

##### type?

```ts
optional type?: string;
```

MIME type, when known.

##### size

```ts
size: number;
```

Size in bytes.

##### modified

```ts
modified: string;
```

Last change, ISO 8601 UTC.

##### writable

```ts
writable: boolean;
```

Whether the app may write it (`files.write` and the user's rights on it).

---

### StorageInfo

A storage request of the manifest and where it stands.

#### Properties

##### id

```ts
id: string;
```

The `id` of the request in the manifest; reach it as `{ storage: id }`.

##### state

```ts
state: StorageState;
```

Whether the storage can be used now.

##### access

```ts
access: 'read' | 'readWrite' | null;
```

What the mapping allows (never more than the manifest requests), or null while it is unmapped.

## Type Aliases

### FileKind

```ts
type FileKind = 'file' | 'folder' | 'symlink' | 'other';
```

What an entry is. Symlinks are listed as themselves and never followed in listings.

---

### FileLocation

```ts
type FileLocation =
  | {
      storage: string;
    }
  | ShareLocation;
```

Where paths start: a named storage from the manifest, or a share by its id (needs `files.shares`). Paths inside are
relative, with `/` as separator, and never leave it; `.` and `..` are refused.

#### Union Members

##### Type Literal

```ts
{
  storage: string;
}
```

###### storage

```ts
storage: string;
```

The `id` of a storage request in the manifest.

---

[`ShareLocation`](#sharelocation)

---

### SortKey

```ts
type SortKey = 'name' | 'size' | 'modified';
```

Order of a folder listing. Name order is natural ("file2" before "file10") and ignores case.

---

### SortOrder

```ts
type SortOrder = 'asc' | 'desc';
```

Ascending or descending; folders count as the smallest size.

---

### FileItems

```ts
type FileItems =
  | {
      names: string[];
    }
  | {
      all: true;
      except: string[];
    };
```

Entries of one folder that an operation works on. `all` with `except` names a whole folder without listing it, so
selecting everything in a folder of 100,000 entries never sends 100,000 names.

#### Union Members

##### Type Literal

```ts
{
  names: string[];
}
```

###### names

```ts
names: string[];
```

The names of the entries, 1 to 1000.

---

##### Type Literal

```ts
{
  all: true;
  except: string[];
}
```

###### all

```ts
all: true;
```

Every entry of the folder.

###### except

```ts
except: string[];
```

Names to leave out, at most 1000.

---

### ConflictPolicy

```ts
type ConflictPolicy = 'fail' | 'skip' | 'overwrite' | 'rename';
```

What happens when the target already has an entry of the same name: `fail` stops the job with [`fs.entry.exists`](https://pithyx.org/docs/reference/errors/#fs.entry.exists),
`skip` leaves the entry out, `overwrite` replaces files and merges folders, `rename` picks a free name such as
"Report (2).pdf".

---

### JobState

```ts
type JobState = 'queued' | 'running' | 'succeeded' | 'failed' | 'cancelled' | 'interrupted';
```

Where a job is: waiting, running, or finished in one of four ways (`interrupted` by a daemon restart).

---

### StorageState

```ts
type StorageState = 'ready' | 'unmapped' | 'locked' | 'unavailable';
```

The state of a storage the manifest requests: `ready` (mapped to a folder that can be reached), `unmapped` (no
administrator assigned a folder yet), `locked` (its pool is encrypted and locked) or `unavailable` (its pool or
folder is missing).
