L'API Accesso al file system consente alle app web di leggere o salvare le modifiche direttamente in file e cartelle sul dispositivo dell'utente.
Che cos'è l'API File System Access?
L'API File System Access consente agli sviluppatori di creare potenti app web che interagiscono con i file sul dispositivo locale dell'utente, ad esempio IDE, editor di foto e video, editor di testo e altro ancora. Dopo che un utente ha concesso l'accesso a un'app web, questa API gli consente di leggere o salvare le modifiche direttamente nei file e nelle cartelle sul suo dispositivo. Oltre a leggere e scrivere file, l'API Accesso al file system offre la possibilità di aprire una directory ed enumerarne i contenuti.
Se hai già lavorato con la lettura e la scrittura di file, gran parte di ciò che sto per condividere ti sarà familiare. Ti invitiamo a leggerlo comunque, perché non tutti i sistemi sono uguali.
L'API File System Access è supportata sulla maggior parte dei browser Chromium su Windows, macOS, ChromeOS e Linux. Un'eccezione degna di nota è Brave, dove è attualmente disponibile solo dietro un flag. Il supporto per Android è in fase di sviluppo nel contesto di crbug.com/1011535.
Utilizzo dell'API File System Access
Per mostrare la potenza e l'utilità dell'API Accesso al file system, ho scritto un singolo editor di testo per file. Ti consente di aprire un file di testo, modificarlo, salvare le modifiche sul disco o avviare un nuovo file e salvare le modifiche sul disco. Non è niente di speciale, ma fornisce informazioni sufficienti per aiutarti a comprendere i concetti.
Supporto browser
Rilevamento di funzionalità
Per scoprire se l'API File System Access è supportata, controlla se esiste il metodo di selettore che ti interessa.
if ('showOpenFilePicker' in self) {
// The `showOpenFilePicker()` method of the File System Access API is supported.
}
Prova
Guarda l'API File System Access in azione nella demo dell'editor di testo.
Leggere un file dal file system locale
Il primo caso d'uso che voglio affrontare è chiedere all'utente di scegliere un file, quindi aprirlo e leggerlo dal disco.
Chiedi all'utente di scegliere un file da leggere
Il punto di contatto dell'API File System Access è
window.showOpenFilePicker()
. Quando viene chiamato, mostra una finestra di dialogo di selezione dei file e chiede all'utente di selezionarne uno. Dopo aver selezionato un file, l'API restituisce un array di handle di file. Un parametro options
facoltativo ti consente di influenzare il comportamento del selettore di file, ad esempio consentendo all'utente di selezionare più file, directory o tipi di file diversi.
Se non vengono specificate opzioni, il selettore di file consente all'utente di selezionare un singolo file. È ideale per un editor di testo.
Come molte altre API efficaci, la chiamata a showOpenFilePicker()
deve essere eseguita in un contesto sicuro e deve essere chiamata all'interno di un gesto dell'utente.
let fileHandle;
butOpenFile.addEventListener('click', async () => {
// Destructure the one-element array.
[fileHandle] = await window.showOpenFilePicker();
// Do something with the file handle.
});
Una volta che l'utente seleziona un file, showOpenFilePicker()
restituisce un array di handle, in questo caso un array di un elemento con un FileSystemFileHandle
contenente le proprietà e i metodi necessari per interagire con il file.
È utile conservare un riferimento all'handle del file in modo da poterlo utilizzare in un secondo momento. Sarà necessario salvare le modifiche al file o eseguire altre operazioni sui file.
Leggere un file dal file system
Ora che hai un handle per un file, puoi recuperare le proprietà del file o accedere al file stesso.
Per ora, leggerò i contenuti. La chiamata a handle.getFile()
restituisce un oggetto File
contenente un blob. Per recuperare i dati dal blob, chiama uno dei metodi (slice()
,
stream()
,
text()
o
arrayBuffer()
).
const file = await fileHandle.getFile();
const contents = await file.text();
L'oggetto File
restituito da FileSystemFileHandle.getFile()
è leggibile solo se il
file di base sul disco non è cambiato. Se il file sul disco viene modificato, l'oggetto File
diventa illeggibile e dovrai chiamare di nuovo getFile()
per ottenere un nuovo oggetto File
che legga i dati modificati.
Riassumendo
Quando gli utenti fanno clic sul pulsante Apri, il browser mostra un selettore di file. Una volta selezionato un file, l'app legge i contenuti e li inserisce in un <textarea>
.
let fileHandle;
butOpenFile.addEventListener('click', async () => {
[fileHandle] = await window.showOpenFilePicker();
const file = await fileHandle.getFile();
const contents = await file.text();
textArea.value = contents;
});
Scrivere il file nel file system locale
Nell'editor di testo, esistono due modi per salvare un file: Salva e Salva con nome. Salva riapplica le modifiche al file originale utilizzando l'handle del file recuperato in precedenza. Tuttavia, Salva come crea un nuovo file e richiede quindi un nuovo handle file.
Crea un nuovo file
Per salvare un file, chiama showSaveFilePicker()
, che mostra il selettore di file in modalità "Salva", consentendo all'utente di scegliere un nuovo file da utilizzare per il salvataggio. Per l'editor di testo, volevo anche che aggiungesse automaticamente un'estensione .txt
, quindi ho fornito alcuni parametri aggiuntivi.
async function getNewFileHandle() {
const options = {
types: [
{
description: 'Text Files',
accept: {
'text/plain': ['.txt'],
},
},
],
};
const handle = await window.showSaveFilePicker(options);
return handle;
}
Salvare le modifiche sul disco
Puoi trovare tutto il codice per salvare le modifiche a un file nella demo del mio editor di testo su
GitHub. Le interazioni di base con il file system si trovano in
fs-helpers.js
. Nella sua forma più semplice, il processo è simile al seguente codice.
Ti illustrerò ogni passaggio.
// fileHandle is an instance of FileSystemFileHandle..
async function writeFile(fileHandle, contents) {
// Create a FileSystemWritableFileStream to write to.
const writable = await fileHandle.createWritable();
// Write the contents of the file to the stream.
await writable.write(contents);
// Close the file and write the contents to disk.
await writable.close();
}
La scrittura dei dati sul disco utilizza un oggetto FileSystemWritableFileStream
, una sottoclasse di WritableStream
. Crea lo stream chiamando createWritable()
sull'oggetto handle del file. Quando viene chiamato createWritable()
, il browser controlla prima se l'utente ha concesso l'autorizzazione di scrittura al file. Se l'autorizzazione di scrittura non è stata concessa, il browser chiede all'utente di autorizzarla. Se l'autorizzazione non viene concessa, createWritable()
lancia un
DOMException
e l'app non potrà scrivere nel file. Nell'editor di testo, gli oggetti DOMException
vengono gestiti nel metodo saveFile()
.
Il metodo write()
accetta una stringa, che è ciò che serve per un editor di testo. ma può anche accettare un BufferSource o un Blob. Ad esempio, puoi inviare uno stream direttamente a
esso:
async function writeURLToFile(fileHandle, url) {
// Create a FileSystemWritableFileStream to write to.
const writable = await fileHandle.createWritable();
// Make an HTTP request for the contents.
const response = await fetch(url);
// Stream the response into the file.
await response.body.pipeTo(writable);
// pipeTo() closes the destination pipe by default, no need to close it.
}
Puoi anche utilizzare seek()
o truncate()
all'interno dello stream per aggiornare il
file in una posizione specifica o ridimensionarlo.
Specificare un nome file e una directory iniziale suggeriti
In molti casi potresti volere che la tua app suggerisca un nome o una posizione predefiniti per il file. Ad esempio, un editor di testo potrebbe suggerire un nome file predefinito Untitled Text.txt
anziché Untitled
. Puoi farlo passando una proprietà suggestedName
come parte delle opzioni showSaveFilePicker
.
const fileHandle = await self.showSaveFilePicker({
suggestedName: 'Untitled Text.txt',
types: [{
description: 'Text documents',
accept: {
'text/plain': ['.txt'],
},
}],
});
Lo stesso vale per la home directory predefinita. Se stai creando un editor di testo, ti consigliamo di avviare la finestra di dialogo di salvataggio o apertura del file nella cartella documents
predefinita, mentre per un editor di immagini ti consigliamo di avviare la finestra di dialogo nella cartella documents
predefinita.pictures
Puoi suggerire una directory iniziale predefinita passando una proprietà startIn
ai metodi showSaveFilePicker
, showDirectoryPicker()
o showOpenFilePicker
, ad esempio in questo modo.
const fileHandle = await self.showOpenFilePicker({
startIn: 'pictures'
});
L'elenco delle directory di sistema note è:
desktop
: la directory del computer dell'utente, se esistente.documents
: la directory in cui in genere vengono archiviati i documenti creati dall'utente.downloads
: la directory in cui in genere vengono archiviati i file scaricati.music
: la directory in cui in genere vengono archiviati i file audio.pictures
: la directory in cui in genere vengono memorizzate le foto e altre immagini fisse.videos
: la directory in cui in genere vengono archiviati i video o i film.
Oltre alle directory di sistema ben note, puoi anche passare un handle di file o directory esistente come valore per startIn
. La finestra di dialogo si aprirà nella stessa directory.
// Assume `directoryHandle` is a handle to a previously opened directory.
const fileHandle = await self.showOpenFilePicker({
startIn: directoryHandle
});
Specificare lo scopo di diversi selettori di file
A volte le applicazioni hanno selettori diversi per scopi diversi. Ad esempio, un editor di testo avanzato può consentire all'utente di aprire file di testo, ma anche di importare immagini. Per impostazione predefinita, ogni visualizzatore di file si apre nell'ultima posizione memorizzata. Puoi aggirare il problema memorizzando i valori id
per ogni tipo di selettore. Se viene specificato un id
, l'implementazione del selettore di file memorizza una directory di ultima utilizzo distinta per quel id
.
const fileHandle1 = await self.showSaveFilePicker({
id: 'openText',
});
const fileHandle2 = await self.showSaveFilePicker({
id: 'importImage',
});
Memorizzazione di handle di file o directory in IndexedDB
Gli handle dei file e delle directory sono serializzabili, il che significa che puoi salvare un handle di file o directory in IndexedDB o chiamare postMessage()
per inviarli tra la stessa origine di primo livello.
Se salvi gli handle di file o directory in IndexedDB, puoi memorizzare lo stato o ricordare su quali file o directory un utente stava lavorando. In questo modo è possibile mantenere un elenco dei file aperti o modificati di recente, offrire di riaprire l'ultimo file quando l'app viene aperta, ripristinare la directory di lavoro precedente e altro ancora. Nell'editor di testo, memorizzo un elenco dei cinque file più recenti aperti dall'utente, consentendo di accedervi di nuovo.
Il seguente esempio di codice mostra la memorizzazione e il recupero di un handle file e di un handle directory. Puoi guardare come funziona su Glitch. Per brevità, utilizzo la libreria idb-keyval.
import { get, set } from 'https://unpkg.com/idb-keyval@5.0.2/dist/esm/index.js';
const pre1 = document.querySelector('pre.file');
const pre2 = document.querySelector('pre.directory');
const button1 = document.querySelector('button.file');
const button2 = document.querySelector('button.directory');
// File handle
button1.addEventListener('click', async () => {
try {
const fileHandleOrUndefined = await get('file');
if (fileHandleOrUndefined) {
pre1.textContent = `Retrieved file handle "${fileHandleOrUndefined.name}" from IndexedDB.`;
return;
}
const [fileHandle] = await window.showOpenFilePicker();
await set('file', fileHandle);
pre1.textContent = `Stored file handle for "${fileHandle.name}" in IndexedDB.`;
} catch (error) {
alert(error.name, error.message);
}
});
// Directory handle
button2.addEventListener('click', async () => {
try {
const directoryHandleOrUndefined = await get('directory');
if (directoryHandleOrUndefined) {
pre2.textContent = `Retrieved directroy handle "${directoryHandleOrUndefined.name}" from IndexedDB.`;
return;
}
const directoryHandle = await window.showDirectoryPicker();
await set('directory', directoryHandle);
pre2.textContent = `Stored directory handle for "${directoryHandle.name}" in IndexedDB.`;
} catch (error) {
alert(error.name, error.message);
}
});
Handle e autorizzazioni di file o directory archiviati
Poiché le autorizzazioni non vengono sempre mantenute tra le sessioni, devi verificare se l'utente ha concesso l'autorizzazione al file o alla directory utilizzando queryPermission()
. In caso contrario, chiama
requestPermission()
per (richiedere di) ottenerne uno. Lo stesso vale per gli handle di file e directory. Devi eseguire fileOrDirectoryHandle.requestPermission(descriptor)
o
fileOrDirectoryHandle.queryPermission(descriptor)
rispettivamente.
Nell'editor di testo ho creato un metodo verifyPermission()
che controlla se l'utente ha già concesso l'autorizzazione e, se necessario, effettua la richiesta.
async function verifyPermission(fileHandle, readWrite) {
const options = {};
if (readWrite) {
options.mode = 'readwrite';
}
// Check if permission was already granted. If so, return true.
if ((await fileHandle.queryPermission(options)) === 'granted') {
return true;
}
// Request permission. If the user grants permission, return true.
if ((await fileHandle.requestPermission(options)) === 'granted') {
return true;
}
// The user didn't grant permission, so return false.
return false;
}
Richiedendo l'autorizzazione di scrittura con la richiesta di lettura, ho ridotto il numero di richieste di autorizzazione. L'utente vede una richiesta quando apre il file e concede l'autorizzazione sia in lettura che in scrittura.
Apertura di una directory ed enumerazione dei relativi contenuti
Per enumerare tutti i file di una directory, chiama showDirectoryPicker()
. L'utente selezione una directory in un selettore, dopodiché viene restituito un FileSystemDirectoryHandle
che consente di enumerare e accedere ai file della directory. Per impostazione predefinita, avrai accesso in lettura ai file nella directory, ma se hai bisogno di accesso in scrittura, puoi passare { mode: 'readwrite' }
al metodo.
butDir.addEventListener('click', async () => {
const dirHandle = await window.showDirectoryPicker();
for await (const entry of dirHandle.values()) {
console.log(entry.kind, entry.name);
}
});
Se devi anche accedere a ogni file utilizzando getFile()
per, ad esempio, ottenere le dimensioni dei singoli file, non utilizzare await
su ogni risultato in sequenza, ma elabora tutti i file in parallelo, ad esempio utilizzando Promise.all()
.
butDir.addEventListener('click', async () => {
const dirHandle = await window.showDirectoryPicker();
const promises = [];
for await (const entry of dirHandle.values()) {
if (entry.kind !== 'file') {
continue;
}
promises.push(entry.getFile().then((file) => `${file.name} (${file.size})`));
}
console.log(await Promise.all(promises));
});
Creazione o accesso a file e cartelle in una directory
Da una directory, puoi creare o accedere a file e cartelle utilizzando il metodo getFileHandle()
o rispettivamente getDirectoryHandle()
. Se passi un oggetto options
facoltativo con una chiave create
e un valore booleano true
o false
, puoi determinare se deve essere creato un nuovo file o una nuova cartella se non esistono.
// In an existing directory, create a new directory named "My Documents".
const newDirectoryHandle = await existingDirectoryHandle.getDirectoryHandle('My Documents', {
create: true,
});
// In this new directory, create a file named "My Notes.txt".
const newFileHandle = await newDirectoryHandle.getFileHandle('My Notes.txt', { create: true });
Risolvere il percorso di un elemento in una directory
Quando lavori con file o cartelle in una directory, può essere utile risolvere il percorso dell'elemento in questione. Questa operazione può essere eseguita con il metodo resolve()
, dal nome appropriato. Per la risoluzione, l'elemento può essere un elemento secondario diretto o indiretto della directory.
// Resolve the path of the previously created file called "My Notes.txt".
const path = await newDirectoryHandle.resolve(newFileHandle);
// `path` is now ["My Documents", "My Notes.txt"]
Eliminare file e cartelle in una directory
Se hai ottenuto l'accesso a una directory, puoi eliminare i file e le cartelle contenuti con il metodo removeEntry()
. Per le cartelle, l'eliminazione può essere facoltativamente ricorsiva e includere tutte le sottocartelle e i file al loro interno.
// Delete a file.
await directoryHandle.removeEntry('Abandoned Projects.txt');
// Recursively delete a folder.
await directoryHandle.removeEntry('Old Stuff', { recursive: true });
Eliminazione diretta di un file o di una cartella
Se hai accesso a un handle di file o directory, chiama remove()
su un FileSystemFileHandle
o
FileSystemDirectoryHandle
per rimuoverlo.
// Delete a file.
await fileHandle.remove();
// Delete a directory.
await directoryHandle.remove();
Rinominare e spostare file e cartelle
I file e le cartelle possono essere rinominati o spostati in una nuova posizione chiamando move()
nell'interfaccia FileSystemHandle
. FileSystemHandle
ha le interfacce secondarie FileSystemFileHandle
e
FileSystemDirectoryHandle
. Il metodo move()
accetta uno o due parametri. Il primo può essere una stringa con il nuovo nome o un FileSystemDirectoryHandle
alla cartella di destinazione. Nel
secondo caso, il secondo parametro facoltativo è una stringa con il nuovo nome, pertanto il trasferimento e la ridenominazione possono essere eseguiti in un solo passaggio.
// Rename the file.
await file.move('new_name');
// Move the file to a new directory.
await file.move(directory);
// Move the file to a new directory and rename it.
await file.move(directory, 'newer_name');
Integrazione con trascinamento
Le
interfacce HTML Drag and Drop
consentono alle applicazioni web di accettare
file trascinati
in una pagina web. Durante un'operazione di trascinamento, gli elementi di file e directory trascinati vengono associati rispettivamente alle voci di file e alle voci di directory. Il metodo DataTransferItem.getAsFileSystemHandle()
restituisce una promessa con un oggetto FileSystemFileHandle
se l'elemento trascinato è un file e una promessa con un oggetto FileSystemDirectoryHandle
se l'elemento trascinato è una directory. La seguente scheda lo mostra in azione. Tieni presente che DataTransferItem.kind
dell'interfaccia di trascinamento è "file"
sia per i file che per le directory, mentre FileSystemHandle.kind
dell'API File System Access è "file"
per i file e "directory"
per le directory.
elem.addEventListener('dragover', (e) => {
// Prevent navigation.
e.preventDefault();
});
elem.addEventListener('drop', async (e) => {
e.preventDefault();
const fileHandlesPromises = [...e.dataTransfer.items]
.filter((item) => item.kind === 'file')
.map((item) => item.getAsFileSystemHandle());
for await (const handle of fileHandlesPromises) {
if (handle.kind === 'directory') {
console.log(`Directory: ${handle.name}`);
} else {
console.log(`File: ${handle.name}`);
}
}
});
Accesso al file system privato di origine
Il file system privato di origine è un endpoint di archiviazione che, come suggerisce il nome, è privato per l'origine della pagina. Sebbene i browser in genere implementino questa funzionalità memorizzando i contenuti di questo
file system privato di origine su disco da qualche parte, non è previsto che i contenuti siano accessibili all'utente. Analogamente, non è previsto che esistano file o directory con nomi corrispondenti ai nomi delle directory secondarie del file system privato di origine. Anche se il browser potrebbe far sembrare che ci siano file, internamente, poiché si tratta di un file system privato dell'origine, il browser potrebbe archiviare questi "file" in un database o in qualsiasi altra struttura di dati. In sostanza, se utilizzi questa API,
non aspettarti di trovare i file creati abbinati uno a uno da qualche parte sull'hard disk. Una volta ottenuto l'accesso alla radice FileSystemDirectoryHandle
, puoi operare come al solito sul file system privato di origine.
const root = await navigator.storage.getDirectory();
// Create a new file handle.
const fileHandle = await root.getFileHandle('Untitled.txt', { create: true });
// Create a new directory handle.
const dirHandle = await root.getDirectoryHandle('New Folder', { create: true });
// Recursively remove a directory.
await root.removeEntry('Old Stuff', { recursive: true });
Accesso ai file ottimizzati per le prestazioni dal file system privato dell'origine
Il file system privato di origine fornisce l'accesso facoltativo a un tipo speciale di file altamente ottimizzato per le prestazioni, ad esempio offrendo l'accesso in scrittura in-place ed esclusivo ai contenuti di un file. In Chromium 102 e versioni successive, è disponibile un metodo aggiuntivo nel file system privato di origine per semplificare l'accesso ai file: createSyncAccessHandle()
(per operazioni di lettura e scrittura sincrone).
È esposta su FileSystemFileHandle
, ma esclusivamente in
Web Workers.
// (Read and write operations are synchronous,
// but obtaining the handle is asynchronous.)
// Synchronous access exclusively in Worker contexts.
const accessHandle = await fileHandle.createSyncAccessHandle();
const writtenBytes = accessHandle.write(buffer);
const readBytes = accessHandle.read(buffer, { at: 1 });
Polyfilling
Non è possibile eseguire il polyfill completo dei metodi dell'API File System Access.
- Il metodo
showOpenFilePicker()
può essere approssimato con un elemento<input type="file">
. - Il metodo
showSaveFilePicker()
può essere simulato con un elemento<a download="file_name">
, anche se questo attiva un download programmatico e non consente di sovrascrivere i file esistenti. - Il metodo
showDirectoryPicker()
può essere in qualche modo emulato con l'elemento non standard<input type="file" webkitdirectory>
.
Abbiamo sviluppato una libreria chiamata browser-fs-access che utilizza l'API File System Access, ove possibile, e passa a queste opzioni di riserva in tutti gli altri casi.
Sicurezza e autorizzazioni
Il team di Chrome ha progettato e implementato l'API File System Access utilizzando i principi fondamentali definiti in Controllo dell'accesso a potenti funzionalità della piattaforma web, tra cui il controllo e la trasparenza per gli utenti, nonché l'ergonomia utente.
Apertura di un file o salvataggio di un nuovo file
Quando apre un file, l'utente fornisce l'autorizzazione per leggere un file o una directory utilizzando il selettore di file.
Il selettore di file aperti può essere mostrato solo utilizzando un gesto dell'utente quando viene visualizzato da un contesto sicuro. Se gli utenti cambiano idea, possono annullare la selezione nel selettore di file e il sito non avrà accesso a nulla. Si tratta dello stesso comportamento dell'elemento
<input type="file">
.
Analogamente, quando un'app web vuole salvare un nuovo file, il browser mostra il selettore per il salvataggio del file, consentendo all'utente di specificare il nome e la posizione del nuovo file. Poiché sta salvando un nuovo file sul dispositivo (anziché sovrascrivere un file esistente), il selettore file concede all'app l'autorizzazione a scrivere nel file.
Cartelle con limitazioni
Per proteggere gli utenti e i loro dati, il browser potrebbe limitare la possibilità di salvare in determinate cartelle, ad esempio le cartelle di sistema operativo di base come Windows, le cartelle Libreria di macOS. In questo caso, il browser mostra una richiesta e chiede all'utente di scegliere un'altra cartella.
Modificare un file o una directory esistente
Un'app web non può modificare un file su disco senza l'autorizzazione esplicita dell'utente.
Richiesta di autorizzazione
Se una persona vuole salvare le modifiche a un file a cui ha precedentemente concesso l'accesso in lettura, il browser visualizza una richiesta di autorizzazione per consentire al sito di scrivere le modifiche sul disco. La richiesta di autorizzazione può essere attivata solo da un gesto dell'utente, ad esempio facendo clic su un pulsante Salva.
In alternativa, un'app web che modifica più file, ad esempio un IDE, può anche chiedere l'autorizzazione per salvare le modifiche al momento dell'apertura.
Se l'utente sceglie Annulla e non concede l'accesso in scrittura, l'app web non può salvare le modifiche al file locale. Deve fornire un metodo alternativo per consentire all'utente di salvare i propri dati, ad esempio offrendo un modo per "scaricare" il file o salvare i dati sul cloud.
Trasparenza
Una volta che un utente ha concesso l'autorizzazione a un'app web per salvare un file locale, il browser mostra un'icona nella barra degli indirizzi. Se fai clic sull'icona, si apre un popup che mostra l'elenco dei file a cui l'utente ha dato accesso. L'utente può sempre revocare l'accesso, se lo desidera.
Persistenza delle autorizzazioni
L'app web può continuare a salvare le modifiche al file senza chiedere conferma finché non sono chiuse tutte le schede per la relativa origine. Una volta chiusa una scheda, il sito perde tutto l'accesso. La volta successiva che l'utente utilizzerà l'app web, gli verrà chiesto di nuovo di accedere ai file.
Feedback
Vorremmo conoscere la tua esperienza con l'API File System Access.
Fornisci informazioni sul design dell'API
C'è qualcosa nell'API che non funziona come previsto? Oppure mancano metodi o proprietà di cui hai bisogno per implementare la tua idea? Hai domande o commenti sul modello di sicurezza?
- Invia una segnalazione relativa alle specifiche nel repository GitHub di accesso al file system WICG o aggiungi il tuo parere a un problema esistente.
Problemi con l'implementazione?
Hai trovato un bug nell'implementazione di Chrome? Oppure l'implementazione è diversa dalla specifica?
- Segnala un bug all'indirizzo https://new.crbug.com. Assicurati di includere il maggior numero di dettagli possibile, le istruzioni per la riproduzione e imposta Componenti su
Blink>Storage>FileSystem
. Glitch è ideale per condividere riproduzioni rapide.
Hai intenzione di utilizzare l'API?
Hai intenzione di utilizzare l'API File System Access sul tuo sito? Il tuo supporto pubblico ci aiuta a dare la priorità alle funzionalità e mostra ad altri fornitori di browser quanto sia fondamentale supportarle.
- Spiega come prevedi di utilizzarlo nel thread di Discourse del WICG.
- Invia un tweet all'indirizzo @ChromiumDev utilizzando l'hashtag
#FileSystemAccess
e facci sapere dove e come lo utilizzi.
Link utili
- Spiegazione pubblica
- Specifica di accesso al file system e Specifica file
- Bug di monitoraggio
- Voce di ChromeStatus.com
- Definizioni di TypeScript
- API File System Access - Modello di sicurezza di Chromium
- Componente lampeggiante:
Blink>Storage>FileSystem
Ringraziamenti
La specifica dell'API File System Access è stata scritta da Marijn Kruisselbrink.