Skip to content

File Fields Upgrade Guide

Stephen Steneker edited this page Jun 23, 2018 · 3 revisions

NOTE this guide and the documentation linked to below are WIP, if this change affects you please help us review and improve them!

As of Keystone v4, the following field types have been replaced by the new File type:

  • AzureFile
  • LocalFile
  • LocalFiles
  • S3File

If you were using these field types in your project, you should instead use File with the appropriate Storage adapter:

There is not yet a Files field type; we are working on implementing nested, repeating Schemas that would effectively replace this, see keystonejs/keystone#3282 for progress.

See the Keystone Storage documentation for a complete API Reference.

Differences between File and LocalFile

Schema

File stores the following schema when used with the FS adapter:

{
    filename: String,       // always on; the filename of the file, including the extension
    size: Number,           // on by default; the size of the file
    mimetype: String,       // on by default; the mime type of the file
    path: String,           // the path (i.e directory) the file is stored in; not the full path to the file
    originalname: String,   // the original (uploaded) name of the file; useful when filename is generated
    url: String,            // publicly accessible URL of the stored file
}
  • you need to explicitly opt-in to the optional schema paths; see the Storage Documentation
  • the filetype path in LocalFile has been replaced by mimetype in File, this may require a schema migration for your application

Options

See the FS Adapter Docs for all available options and their usage.

  • format has been removed, we may introduce equivalent functionality in the File field
  • dest has been replaced by the fs.path Storage option
  • prefix has been replaced by the fs.publicPath Storage option, setting this will cause the url schema path to be populated with ${fs.publicPath}${file.filename}
  • datePrefix has been removed
  • allowedTypes has been removed, we may introduce equivalent functionality in keystone.Storage
  • filename has been replaced by the fs.generateFilename option

The generateFilename() method no longer receives a reference to the item being updated, we may introduce this in a future update.

Other functionality may be slightly changed or missing in the first release. Please open an issue if you have trouble using the new File field or Storage API, or if you have difficulty migrating data. PRs are very welcome.

Uploading Files

Previously you would upload files using the UpdateHandler by providing a ${path}_upload file field in a multipart encoded HTML Form.

You now need to specify only the field path, without the _upload suffix. For example:

<!-- old -->
<input type="file" name="myFileField_upload">
<!-- new -->
<input type="file" name="myFileField">

Example

To update the following schema for Keystone v4:

MyList.add({
  someFile: {
    type: Types.LocalFile,
    dest: '/data/files',
    prefix: '/files/',
  }
});

You would now do the following:

var myStorage = new keystone.Storage({
  adapter: keystone.Storage.Adapters.FS,
  fs: {
    path: 'data/files',
    publicPath: '/files',
  },
});

MyList.add({
    someFile: { type: Types.File, storage: myStorage },
});

Differences between File and S3File

See the differences between File and LocalFile above; this section only describes differences unique to S3File.

Options

  • s3path has been replaced by the s3.path Storage option
  • headers has been replaced by the s3.headers Storage option

The 'headers' option now only supports an object in the format { 'header': 'value' }, and not an Array or Function as in S3File. We may introduce support for other formats in a future update.

Example

To update the following schema for Keystone v4:

MyList.add({
  someS3File: {
    type: Types.S3File,
    s3path: '/uploads',
    headers: {
      'x-amz-acl': 'public-read',
    },
  }
});

You would now do the following:

var s3Storage = new keystone.Storage({
  adapter: require('keystone-storage-adapter-s3'),
  s3: {
    path: 'uploads',
    headers: {
      'x-amz-acl': 'public-read',
    },
  },
});

MyList.add({
    someFile: { type: Types.File, storage: s3Storage },
});