diff --git a/blog/2024-07-10-uppy-4.0.md b/blog/2024-07-10-uppy-4.0.md index eaeee34df..60114d137 100644 --- a/blog/2024-07-10-uppy-4.0.md +++ b/blog/2024-07-10-uppy-4.0.md @@ -1,7 +1,7 @@ --- title: 'New Uppy 4.0 major: TypeScript rewrite, Google Photos, React hooks, and much - more.' + more' date: 2024-07-10 authors: [aduh95, evgenia, mifi, murderlon] image: /img/blog/4.0/preview.jpg @@ -10,30 +10,30 @@ published: true toc_max_heading_level: 2 --- - + Hold on to your leashes, folks! Uppy 4.0 is here, and it’s more exciting than a tennis ball at the dog park! Our beloved Uppy mascot, the adorable coding canine, has been hard at work fetching all the latest updates for you. From a full TypeScript makeover to shiny new React hooks, and even Google Photos -integration, this release is packed with treats that will make developers wag -their tails in delight. So, sit, stay, and let’s dig into what makes Uppy 4.0 -the goodest of good boys in file uploading! +integration – this release is so packed with treats that we're almost wagging +our tails in excitement. Without further a-dog, let’s dig into what makes Uppy +4.0 the goodest of good boys in file uploading! ## Migration guide -This post goes into the most exciting new features of Uppy 4.0. We have an +This post covers the most exciting new features of Uppy 4.0. We have an accompanying [migration guide](/docs/guides/migration-guides/) to help you transition to 4.0. ## TypeScript rewrite -In the year 2024 people expect excellent types from their libraries. We used to -author types separately by hand but they were often inconsistent or incomplete. -Now Uppy has been completely rewritten in TypeScript! +In the year 2024, people expect excellent types from their libraries. We used to +author types separately by hand, but they were often inconsistent or incomplete. +As of now, Uppy has been completely rewritten in TypeScript! From now on you’ll be in safe hands when working with Uppy, whether it’s setting the right options, building plugins, or listening to events. @@ -49,13 +49,13 @@ uppy.on('file-added', (file) => { }); ``` -One important thing to note are the new generics on `@uppy/core`. +One important thing to note is the new generics on `@uppy/core`. ```ts import Uppy from '@uppy/core'; -// xhr-upload is for uploading to your own backend. +// xhr-upload is for uploading to your own back end. import XHRUpload from '@uppy/xhr-upload'; // Your own metadata on files @@ -86,8 +86,8 @@ Happy inferring! ## Merging the two AWS S3 plugins -We used to have two separate plugins for uploading to S3 (and S3-compatible -services): `@uppy/aws-s3` and `@uppy/aws-s3-multpart`. They have different use +We used to have two separate plugins for uploading to S3 and S3-compatible +services: `@uppy/aws-s3` and `@uppy/aws-s3-multpart`. They have different use cases. The advantages of multipart uploads are: - Improved throughput – You can upload parts in parallel to improve throughput. @@ -105,33 +105,33 @@ uploading files that are only a couple kilobytes with a 100ms roundtrip latency, you are spending 400ms on overhead and only a few milliseconds on uploading. This really adds up if you upload a lot of small files. -AWS, and generally the internet from what we found, tend to agree that **you -don’t want to use multipart uploads for files under 100MB**. But this sometimes -puts users of our libraries in an awkward position, as their end users may not -only upload very large files, or only small files. In this case a portion of -their users get a subpar experience. +AWS – and the internet in general, from what we found – tends to agree that +**you don’t want to use multipart uploads for files under 100 MB**. This +sometimes puts users of our libraries in an awkward position, though, as their +end users may not exclusively upload very large files, or only small files. +In this case, a portion of their users get a subpar experience. --- We’ve merged the two plugins into `@uppy/aws-s3` with a new -[`shouldUseMultipart`](/docs/aws-s3/#shouldusemultipartfile) option! By default -it switches to multipart uploads if the file is larger than 100MB. You can pass -a `boolean` or a function to determine it per file. +[`shouldUseMultipart`](/docs/aws-s3/#shouldusemultipartfile) option! By default, +it switches to multipart uploads if the file is larger than 100 MB. You can pass +a `boolean` or a function to determine this per file. ## React hooks People working with React are more likely to create their own user interface on -top of Uppy than those working with “vanilla” setups. Working with our pre-build +top of Uppy than those working with “vanilla” setups. Working with our pre-built UI components is a plug-and-play experience, but building on top of Uppy’s state with React primitives has been tedious. -To address this we’re introducing to new hooks: `useUppyState` and +To address this, we’re introducing two new hooks: `useUppyState` and `useUppyEvent`. Thanks to the TypeScript rewrite, we can now do powerful inference in hooks as well. ### `useUppyState(uppy, selector)` -Use this hook when you need to access Uppy’s state reactively. +Use this hook when you need to read Uppy’s state. ```ts import { useState } from 'react'; @@ -144,7 +144,7 @@ const [uppy] = useState(() => new Uppy()); const files = useUppyState(uppy, (state) => state.files); const totalProgress = useUppyState(uppy, (state) => state.totalProgress); -// We can also get specific plugin state. +// We can also get a specific plugin state. // Note that the value on `plugins` depends on the `id` of the plugin. const metaFields = useUppyState( uppy, @@ -154,8 +154,11 @@ const metaFields = useUppyState( You can see all the values you can access on the [`State`](https://github.com/transloadit/uppy/blob/dab8082a4e67c3e7f109eacfbd6c3185f117dc60/packages/%40uppy/core/src/Uppy.ts#L156) -type. If you are accessing plugin state, you would have to look at the types of -the plugin. +type. + +Using this hook, you can also access the state of any Uppy plugin. For example, +in order to access the state of `ImageEditor`, you would have to look at the +types of the plugin. ```ts import type { State } from '@uppy/core'; @@ -166,12 +169,12 @@ import type { State } from '@uppy/core'; Listen to Uppy [events](/docs/uppy/#events) in a React component. The hook returns `[results, clear]`. `results` is an array of values from the -event. Depending on the event, that can be empty or have up to three values. +event. Depending on the event, this can be empty or have up to three values. `clear` is a function to clear the `results` array. -Values remain in state until the next event (if that ever comes) or if the state -is manually cleared. Depending on your use case, you may want to keep the values -in state or clear the state after something else happened. +Values remain in state until the next event (if that ever comes) or the moment +when the state is manually cleared. Depending on your use case, you may want +to keep the values in state or clear the state after something else happened. ```ts import { useState } from 'react'; @@ -193,40 +196,42 @@ useUppyEvent(uppy, 'cancel-all', () => { ## Google Photos -A long requested feature is finally here: Google Photos support! +An often requested feature is finally here: Google Photos support! :::info Uppy can bring in files from the cloud with [Companion](/docs/companion/). -Companion is a hosted, standalone, or middleware server to take away the +Companion is a hosted, standalone, or middleware server that takes away the complexity of authentication and the cost of downloading files from remote sources, such as Instagram, Google Drive, and others. -This means a 5GB video isn’t eating into your users’ data plans and you don’t -have to worry about OAuth. +This means a 5 GB video isn’t eating into your users’ data plans and you +don’t have to worry about OAuth. ::: -[`@uppy/google-photos`](/docs/google-photos/) is a new plugin so you can use it -next to your existing [`@uppy/google-drive`](/docs/google-drive/) plugin. +[`@uppy/google-drive`](/docs/google-drive/) and +[`@uppy/google-photos`](/docs/google-photos/) are separate plugins. However, +you can use the same OAuth app for both these plugins. Be sure to enable +"Photos Library API" in your OAuth app, though! ## UX improvements for viewing remote files When using [Dashboard](/docs/dashboard) with any of our remote sources (Google Drive, Facebook, etc.) you use our internal `@uppy/provider-views` plugin to -navigate and select files. In Uppy 4.0, we are making a handful of quality of -life improvements for users. -We describe the main changes in a table below. +navigate the folders and select files. In Uppy 4.0, we are making a few quality +of life improvements for users. The main changes are described in the table +below.
Folder states: checked, unchecked, partial
- In 4.0, we introduce a new folder state - a "partially checked" folder. A folder acquires this state when some files within the folder are "checked", and some files are "unchecked". +In 4.0, we introduce a new folder state – a "partially checked" folder. A folder acquires this state when certain files within the folder are "checked", and other files are "unchecked". |
|
Cache
- When navigating in and out of folders, you no longer have to wait for the same API call — results get cached. +When navigating in and out of folders, you no longer have to wait for the same API call — results are cached. |
|
Restrictions
- Uppy supports file restrictions, such as maximum number of files and maximum file size. In 4.0, we reworked our restrictions UI - users will get immediate feedback upon exceeding the number of selected files, and users get a chance to reenter the correct number of files after their first upload attempt. + Uppy supports file restrictions, such as maximum number of files and maximum file size. In 4.0, we reworked our restrictions UI – users will get immediate feedback upon exceeding the number of selected files, and get a chance to re-enter the correct number of files after their first upload attempt. |