The filesystem
For reading and writing files, ArcOS has the Filesystem kernel module. This module is accessible globally (defined as the fs
constant) or as a property in every process (Process.fs
). You can use this module to perform various filesystem operations on any mounted drive.
Dispatches
As discussed on the Built-in utilities (namely util.onFileChange
and util.onFolderChange
), the ArcOS filesystem dispatches changes to the filesystem across the operating system for other applications to listen to.
ArcOS does this internally in various different ways, but what you need to know is that any dispatch
argument in the Filesystem kernel module defaults to true
. Set it to false
to prevent ArcOS from informing the rest of the operating system of the operation. This is handy if you want to perform a bunch of filesystem operations without updating everything else at the same time.
If you want to perform a bunch of filesystem operations sequentially, disable dispatch on all of them, and then manually dispatch the changes you've made using:
dispatch.dispatch("fs-flush-folder", path); // for folders
dispatch.dispatch("fs-flush-file", path); // for files
Reading a file into RAM
To read a file, call fs.readFile
, passing in the path to the file you want to read:
const contents = await fs.readFile("T:/test.txt");
readFile
returns an ArrayBuffer
or undefined, depending on whether or not the file exists. You can then use convert.arrayToText
to convert this array buffer to a string. For more information, visit the Data conversion page.
Writing a file
Similar to readFile
, writeFile
takes a path and some content to write to it. Here's the type for the writeFile
method:
writeFile(path: string, data: Blob, onProgress?: FilesystemProgressCallback, dispatch?: boolean): Promise<boolean>;
The onProgress argument is the same across all filesystem operations. See Filesystem progress for more information.
Creating a directory
To create a directory, call fs.createDirectory
, passing in the path you want to create. Recursive creations aren't supported, though might work depending on the drive. The function returns true
if the folder was created, or false
if it wasn't.
createDirectory(path: string, dispatch?: boolean): Promise<boolean>;
Moving and copying items
The moveItem
and copyItem
functions are very limited at this time. They take one source and one destination. The source can either be a file or a folder, and the destination indicates the directory the source will be copied to. You also cannot copy or move items across drives. This functionality will be implemented in the future.
To move an item, call fs.moveItem
:
moveItem(source: string, destination: string, dispatch?: boolean): Promise<boolean>;
To copy an item, call fs.copyItem
:
copyItem(source: string, destination: string, dispatch?: boolean): Promise<boolean>;
Direct file access
If you need a link to a file that you can use directly in an HTML element like an image or an audio fragment, call fs.direct
:
direct(path: string): Promise<string | undefined>;
This will return an accessor link generated by the backend. File accessors are stored in the database, linked to your user. Accessor links expire after 24 hours. If you call fs.direct
on the same link, the same accessor will be returned instead of a new one. Here's an example of a direct file access:
const image = document.createElement("img");
img.src = await fs.direct(util.join(, "minesweeper.png"));
this.()?.append(img);
Filesystem progress
When performing a large file operation, like uploading a file or mounting a drive, you're advised to keep the user informed using the FilesystemProgressCallback
. Before you start the operation, creata an FsProgress instance, and then stop it when it's done. Take this example from the Writer app:
const prog = await daemon.FileProgress({
type: "size",
caption: `Reading file`,
subtitle: path,
icon: TextMimeIcon,
}, this.pid);
const contents = await fs.readFile(path, (progress) => {
prog.setWait(false);
prog.setWork(true);
prog.show();
prog.setMax(progress.max);
prog.setDone(progress.value);
});
prog.stop();
Do note that this snippet includes variables that aren't accessible, like path
and TextMimeIcon
. As you can see I'm calling several properties of the prog
variable. These are functions you can call to change the file progress. The properties are here.
The FileProgress
method is asynchronous: it has to be awaited to prevent conflicts in the proces stack.
You might have to make the total value one value higher than the completed value to prevent the file progress from automatically closing if there are multiple file operations you want to display using one file progress. Keep that in mind.
Properties of a FileProgress
progress
Svelte Store
-
Returns the current state of the file progress
mutateMax
Function
number
Adds or subtracts from the total value
mutDone
Function
number
Adds or subtracts from the completed value
updateCaption
Function
string
Changes the file progress' caption.
updSub
Function
string
Changes the subtitle below the caption
setMax
Function
number
Sets the total value
setDone
Function
number
Sets the completed value
setWait
Function
boolean
Turns on or off the "wait" indicator
setWork
Function
boolean
Turns on or off the working
indicator
mutErr
Function
string
Appends an error to the list of errors
stop
Function
-
Stops the file progress
show
Function
-
Shows the file progress (it's hidden initially)
setCancel
Function
function or undefined
Gives the cancel
button an action, or disables it
setType
Function
"none" | "quantity" | "size"
Sets the type of file progress you're displaying.
Uploading files
For uploading files, ArcOS has yet another method in the Filesystem kernel module you can access, named uploadFiles
, which is basically just a glorified wrapper for an input[type="file"]
. Here's the syntax for it:
uploadFiles(
target: string,
accept?: string,
multiple?: boolean,
onProgress?: FilesystemProgressCallback
): Promise<UploadReturn>;
target
specifies the directory you want to upload to, accept
is the same as the DOM's accept attribute, multiple
specifies if the host operating system's file picker should allow a single file or multiple files for uploading. Finally, theres onProgress
, which is the same as any other progress callback in this kernel module. Learn more about filesystem progress here.
Last updated