[MUSIC PLAYING] PHIL ADAMS: Hello, everyone. It's great to be here
with you all today. My name is Phil Adams, and I'm
a researcher here at Google. PIERRE LECESNE: And
I'm Pierre Lecesne, software engineer at Google. PHIL ADAMS: We are here
to talk to you today about how we're rethinking app
distribution on Google Play. We'll talk about the new
app publishing format that we announced at I/O
and share some new features that we've been working on,
digging deeper into some of the topics that you saw
covered during the keynote. To start with, let's talk
about app size and the impact that it's having on your app. Why does app size even matter? We shared this
chart at Google I/O, and you saw it earlier today. Play Store data does show
that when the app gets bigger, install success rate goes down. Many users don't have enough
space left on their device, and especially in emerging
markets, data can be expensive, and connection speeds slow. I want you to think about
your own experience, too. How many of you
have seen a warning from Play to uninstall apps? Millions of people see
things like this everyday. We've started looking into
this area more closely, and we have found
that freeing up space is a major driver of uninstalls. PIERRE LECESNE:
This is obviously a problem for people
with low-storage devices, but it's also a problem for
people with high-end devices who fill up their
devices with HD content. Take the US and the UK. One in five [INAUDIBLE]---- one
in five devices have very low storage and are reaching the
limit where they can't install or update. A key request we
hear from developers is also for help understanding
and reducing uninstalls. We ran a user research
study last year to look into why users
in the US uninstall apps. The leading reason apps were
uninstalled straight away, within a day, was quality. However, the leading
reason apps or games were uninstalled after a
month was to free up space. Apps and games keep
getting bigger. Since 2012, apps
and games have grown over five times on average. Newer devices have more
storage, but the apps, games, high-res photos, and HD videos
keep getting bigger, too. Making your app
big puts it at risk to suffer from all
these downsides. Bigger app lose acquisitions,
and bigger apps also get uninstalled
to free up space. I'm sure you already know
that, and you've probably just considered it a tradeoff. Do you add new features
and support more device configurations,
but lose installs and drive more uninstalls? We don't want you to have to
worry about these tradeoffs. For a few years,
there has been a way to optimize for
device configurations. You can use multiple APKs. But it's incredibly inefficient,
and it's a painful process. This is what it looks like
in the Play Console when you have to upload dozens of
APKs for a single release. The number of APKs grows
quickly across dimensions-- for example, 64-bit, 32-bit,
and all the screen densities, and you have to version
every APK for each release. It also doesn't help with
some of the dimensions. For example, all the
languages are still in all the APK-- in every APK. We can do better. Let us show you the solution
that we have built for this and see how the new app model
helps make your life easier. PHIL ADAMS: So the
new app model is focused on improving the
whole user acquisition journey, from discovery
through to retention. It helps by making your app
smaller, directly improving install and uninstall rates. And in addition
to that, it makes your releases more manageable. In that context, for the
rest of today's session, we'll talk about
three important steps that we want to help you with. First, we want to help you
convert more installers and minimize uninstalls
by building smaller apps. Then we want to make
it possible for you to deliver different features to
different audiences on demand, only for those
users who need them. And finally, we want to help
you keep your users up to date on the latest and greatest
versions of your app. Let's start with how to
make your app smaller. This is where we began with
our major announcement at I/O about the Android App Bundle. The App Bundle is the official
Android app publishing format. Apps that have already
adopted the bundle are seeing an average
size saving of 35%. That's compared to a universal
APK, and that's quite a lot. How does adopting a bundle
lead to such savings? Here's the big idea. Google Play can
assist and take care of delivering just what's needed
to each device on your behalf. There's no need to send a
bunch of languages and device resources, which
are not necessary. We support three slicing
dimensions out of the box-- languages, screen densities,
and CPU architecture. All of this is made
possible by split APKs, a feature we added to
the Android platform in Android Lollipop. Split APKs allow multiple APKs
to be installed on a device and behave as if they're
part of the same app. These split APKs
can be installed in different combinations
on different devices and can be installed all at
once upfront or over time, piece by piece. Given a bundle,
Google Play starts by putting everything that
is common to all devices in the base APK. This includes the Android
manifest and the dex files, for instance. We then generate a
different split APK for each screen density. Each split will contain
all the drawables that would have been selected
by the Android framework on that device
with that density. We then also generate
different split APKs for each native
architecture, and we can generate a separate split
for each language supported by your app, putting
each language's strings in a different APK. Together, we call these
splits configuration splits, or config splits. PIERRE LECESNE: Now, when we
go to serve an app to a device, we only need to serve a
subset of these splits. So if Phil, for example,
has a Samsung Galaxy J5, we will install the base APKs,
as well as the xhdpi density split, the arm architecture
split, and the English language split. But it can get a bit
trickier than that. I speak both French
and English, and I have specified both languages
in my device settings. So my Pixel 2XL will not only
receive the correct density and architecture split,
but also the French and the English language splits. And if I then move to
Brazil and learn Portuguese, I might add Portuguese as
a language on my device. When I do this,
the Play Store will attempt to download the
Portuguese language split for all the apps on my phone. For devices pre-L which
don't support split APKs, Play will generator a
matrix of standalone APKs for each combination of
API and screen density that your app supports. Each of these APK
contains all the files necessary for the device, so my
old Galaxy Nexus still running Android KitKat would receive
the hdpi API and arm APK. Note that all the languages
are included in those APKs. Putting it all together,
the picture looks like this. You actually don't need to worry
about all the details of how these APKs are generated. All you have to do is
upload a single app bundle, and Play generates and
selects the right things to serve for each device. To summarize-- the App
Bundle contains everything. Play processes the bundle,
generates optimized APKs, and then signs each APK to
deliver to user devices. Note that because Play
is now sending the APKs, this means that you need
to upload your signing key to Google Play. This is part of the program
called App Signing by Play. In conversations we've
had with developers, they've asked a
reasonable question. Is this secure? The answer is absolutely. As you can imagine, Google
takes this very seriously. We protect your key
in the same storage we protect Google's own keys. We have engineers
for custom security, and you'll benefit from
our ongoing investments. PHIL ADAMS: We've been
chatting to developers who are already using the App
Bundle about what they like. Recently, we've
conducted a workshop with some developers from India
who make really popular apps. These developers have
millions of active installs, and they're very
sophisticated about keeping their app size small
because their users are very sensitive to it. So this is a useful group
for us to learn from. Riafy found that
smaller installs improve their conversion rates. RedBus speaks to
their release process being more streamlined
and easier to manage. And Swiggy reports that
switching was a simple process, and they were testing using
the bundle within an hour. And it's not just developers
in India, of course. All these developers
around the world have switched and are seeing
fantastic size savings. Duolingo, for example,
saw a 56% size saving compared to a universal
APK, and it's really hard to get such big savings from
incremental optimizations. Switching to the
bundle is the simplest and highest-impact thing
that most developers can do to reduce app size. Google apps are also adopting
the bundle in production, and they're seeing
strong savings as well. Google Maps is saving about
15% in size; YouTube, 24%; Google News, 27%. They also report some
streamlining of their release process and have even noticed
a lift in update rates. So you can see this
isn't experimental. This is ready. There are thousands of apps-- thousands of app
bundles in production, and it's time for all
developers to start moving towards this
new publishing format. PIERRE LECESNE: So when
you adopt the App Bundle, you're not only gaining
size savings today. You will also be benefiting
from automatic optimizations in the future as
Play introduces them. Here's a cool example
of another optimization we're just introducing. We've added a new Android
platform optimisation to the App Bundle called
Uncompressed Native Libraries. Here's how it works. On Android L and
below, native libraries have to be uncompressed
from the APK before the platform
can use them, meaning the user ends up with
two copies of the library. After Android M, the
platform can read the library directly from the APK if it's
left uncompressed, thus saving a copy on the device. To do it yourself, you
will need to upload two versions of your app
and create multi APK for pre and post M. If you're
using the App Bundle, you just give us your libraries,
and we create the required flavor for pre and post
M and serve the right APK to the right user. The size savings we're
seeing on average are significant-- around 16%
reduction in size on disk and 8% reduction
in download size. As I explained, the
app is smaller on disk because the platform
does not need to make a copy of the
library, but the download size is also smaller because our
compression algorithms perform much better on data that
is not already compressed. Our partner Gameloft saw size
savings on disk of 22% and 16% on the download size for
their game "My Little Pony" using this optimization
in the App Bundle. And these savings
are in addition to the size savings
they're already seeing from switching
to the App Bundle. With this optimization, the
download is size is smaller, it's faster to install, and
takes up less space on disk. If you're using the App Bundle,
you get this new optimization without any extra effort. Now, we still want you
to remain in control to when these optimizations
should be pushed to your users. For that reason, Play will
only apply optimizations on App Bundle that
have been built with the version of Gradle that
introduces the optimization. For example, the Uncompressed
Native Libraries optimization will only be applied to
your app if you build it with the latest Gradle
3.3, which is already available for download in beta. PHIL ADAMS: Now,
let's take a look at how you can build, test, and
publish Android app bundles. You can build app bundles
in the 3.2 stable release of Android Studio. The build process is
very similar to building an APK for most developers,
so it's easy to switch. For those who prefer
the command line or wish to integrate with
automated build systems, the new Gradle Android plugin
provides a new set of tasks to build Android app bundles. As you'll remember, you
would use the assemble task on the command line
for building APKs, and now with the
Android App Bundle, you use the new bundle task. Similar to assemble
tasks, bundle tasks also allow you to
build specific flavors. The bundle task will generate
an Android App Bundle and place it in the Outputs
folder with the flavor and build type chosen. The build artifact is
simply called bundle.aab. We do want developers to retain
control over their splits, and so for, if any reason,
you need to disable splitting by a particular dimension, you
can do so using the new bundle block as shown here. Android Studio and Gradle
are not the only ways that you can build bundles today
because the format and bundle tool are open source. Others are already
adopting them. For example, we're excited to
share that games using Unity can now build Android
app bundles, too. Unity added support in
the 2018 0.3 beta release, and you can join the
beta program now. PIERRE LECESNE: So now let's see
how you can adapt your testing with the App Bundle. During the development
phase, when you need to iterate
quickly, you don't need to go through the App Bundle. You can keep building
APKs directly from Studio. Much faster. Before a release,
you may want to test the APKs that would be
generated from the App Bundle. From Studio, this is as
easy as creating a new run configuration and
selecting APK from App Bundle in the deploy menu. Studio, under the hood, uses
the same tool, Playtest, to generate the APKs, so
you'll get high fidelity. When you want to share the APKs
generated from the App Bundle, say with your QA team, you
can use the bundletool command line. This tool is what Play and
Gradle use under the hood to generate APKs. We have open source bundletool
to be transparent about how we generate APKs,
and you can download the bundletool library on
the GitHub repo you see here. Bundletool generates what we
call an APK set archive, which will contain all the
APKs for all the devices that your app supports. We can share this archive,
and still using bundletool, you can install it on a
connected device, which will simulate what Play
does when serving APKs to that device. As you can imagine, an APK
set can become quite big, so if you want to build the
APKs only for a given device configuration, you can do so by
passing to bundletool a device specification in a JSON format. We can share that
archive around, which can then be installed on
the devices matching the spec. This is what the command line
looks like to build an APK set archive from the App Bundle. In this case, we're instructing
bundletool to build APKs only for the connected device. If you don't have
a device at hand-- if you're generating the archive
from a CI system, for example-- you can pass, instead,
a device specification in this JSON format. Finally, if you want a
unique, easily sharable APK, you can also choose to
build a universal APK. This APK does not
use splits, but it can be installed on
any device, so it is very convenient for sharing. But the best way to test
exactly what your users will get is still to go through
the internal test track on the Play Console. This way, you are
guaranteed to get, byte for bytes, what
your users will get. The internal test track is
similar to the alpha and beta tracks that you may
already be familiar with, but it differs from these
tracks in that there is almost no delay
between the upload of the bundle and the update
being available on the tester's device. You can see, here, how it
looks in the Play Console. You can create a list of emails
for up to 100 QA testers. The QA testers can then
follow the update link, and they'll receive,
automatically, the latest version. We know that, for some of you,
these testing options are not ideal. And we see a gap in particular
between testing in Android Studio and Play's test tracks. So I just want you
to know that we're thinking really hard about
how to close this gap. PHIL ADAMS: So now, you've
built and test bundles. Let's discuss publishing
bundles and also a new view that we've added to
the releases section. In the Play Console,
we're starting to show an estimate when we
think that an app could really benefit from using
the App Bundle. We'll take a common
reference device and calculate what
you could save were you switch to the bundle. Once you choose to switch,
you manage your release just like you did with APKs. Simply create a new release
and drop the App Bundle in the same location where
you currently drop your APKs. Do note, in order to
aid your migration, you can keep uploading APKs
on your production track while you test the
bundle in a test track. And when you do this, Play is
not going to reassign the APK. We did this so that
you can feel confident trying out the App Bundle
with a smaller number of users first without affecting your
current production user base. Once you've uploaded it,
you review your release, you roll it out, and that's it. I can't stress this enough. As Pierre mentioned, there's
no more multi APK to deal with. Play Console has created
in the background all the APKs for the
devices supportive for you. Now that you've uploaded
your App Bundle, and Play has done
this heavy lifting, it would be really nice to
have an overview of what Play has generated for you. To give you this
transparency, we've built a new tool in the Play
Console called Bundle Explorer, which lets you navigate
your uploaded bundles and the generated artifacts. On the first screen
of Bundle Explorer, you'll see how much
of a size savings you've gained by
publishing a bundle. Of course, this is going to
be different device by device, and so we calculate this using
a popular device configuration. You can also see below a
list of device configurations and the total size of the HP
case served to those devices. If you click on
View Devices, you can see which devices
are in each bucket. Alternatively, you can search
for supported device by name to download the set of
generated APKs that gets served to that specific device. And this is
particularly helpful, for example, when you get a bug
report for a particular device. So you can get the
exact same APKs that Play has served to it. Of course, we haven't
forgotten about everyone who uses our publishing API. Uploading bundles is also
available via the API, and automation and CI tools are
already adopting the bundle-- for example, Fast Lane. You'll find all the
documentation at these URLs. PIERRE LECESNE: To recap, that's
the latest on the Android App Bundle and how we're making
your apps smaller and releases simpler. The next big change the
App Bundle introduces is modularization and
dynamic code loading. This is an approved,
safe way to load features and functionality dynamically,
making your app even smaller at install time. Let me tell you how it works. Dynamic features
offer yet another way you can reduce the
size of your app. Some big features in your
app may be used by only 10% of your users, so to avoid
having the 90-other percent pay the price of disk space for
a feature they don't use, you can choose to extract it in
what we call a dynamic feature. Dynamic features
can be installed on demand when
user requests them, or you can choose to defer
installing them to a later time when the app goes
to the background. For pre-L devices, which don't
support on-demand features, we can fuse the modules
into the main app so they're delivered
at install time. All of these use cases are
supported in production to date, with millions of
users benefiting already. Facebook was actually one
of our launch partners, and they are using dynamic
features in production across their app portfolio. Let's take a look
at their story. PHIL ADAMS: App size is
really important to Facebook. They evaluate the
app size impacts of each new feature
carefully to ensure that the benefit of the feature
is worth the size increase. Dynamic features means that
they can build new features without increasing the size of
apps like Facebook and Facebook Lite at install time. Dynamic features
also help Facebook with their high-end
device strategy. Facebook is able to
deliver advanced features to just supported devices. And they can also
remove large features that are not used often to avoid
taking up space on that device forever. Facebook has told us that
dynamic features work well when they're working
on a new feature that is separate from the main app. They can have a separate team
of engineers working on it. They can then add it to the app
without increasing the base app size at install time. Here are some of the
examples of dynamic features that Facebook has
added to their apps. These are all features
that are in production. For example, card
scanning is a feature that only a small percentage
of Facebook's users are using, so moving it to
a dynamic feature avoids it taking
up two megabytes on every user's device for
the lifetime of that app. Another example is
real-time communication. By moving voice and video
chat to a dynamic feature, only users with devices
that can support them, and who actually want to use
them, need to download it. What might that experience
look like for a user? Let's take a simple example. Imagine that you
have a recipe app, and you want to keep the
initial download size small. You observe that,
while all of your users like to browse for recipes,
only a small fraction of them like to add recipes,
and you notice that this functionality takes
up significant size in your app. You can choose, therefore,
to break this feature out into its own module and
serve it only when needed. We can see what it
looks like for the user, or what it might look
like for the user, here. The app opens, and then the
user goes to add a recipe. The app then requests that
the module be installed. It's downloaded and
installed with progress visible to the user,
and the new feature is ready to be used
after just a few seconds. Which parts of your app
might make good candidates to be broken out as
separate features? We think about it using
this Venn diagram. If only a smaller fraction of
your users use this feature, it could be a good
candidate, especially if that feature takes up
significant amounts of space. And finally,
consider if users can wait a few seconds before
downloading and using that feature. If you're interested in
modularizing your app, I invite you to check
out the Plaid 2.0 project that some of our dev
roles have been working on and the associated articles
that they published that describe how modularization
was achieved for the app. PIERRE LECESNE: Now
that we have covered how dynamic features work,
let's see how to create them. To create a dynamic module
in Android Studio 3.2, all you need to do is use the
new dynamic feature wizard. Click on File, New Module, then
choose Dynamic Feature Module. Just type in your module's
name, and Android Studio will generate a new
dynamic feature for you. Under the hood, this
is what Studio does. In the manifest of
your new module, a split identifier is added. In this case, we'll
call it Add Recipe. This is how the Android
platform recognizes that, although this APK
has the same package name, it's still a different module. Then a new module
tag element is added, which allows to
configure distribution aspects of the module. This tag is used
by the Play Store to read properties of
the modules of your app. Next, you declare that this
module is an on-demand module by adding the On
Demand attribute, meaning that it will be only
delivered to users' devices when you request it
instead of at install time. Note that on-demand modules are
only supported since Android L, so you have to
specify as well what Play should do with
this module when it generates the pre-L APKs. You can choose to fuse
that module into base APK or exclude it completely. And this is configured
using the Fusing tag. Here's an example
with our recipe app. In addition to the base module,
we have two dynamic features. The Add Recipe module is
marked with Fuse Equal True, while the
other VR module is marked with Fuse Equal False. And you can see that Play will
only include the Add Recipe module in the pre-L APK. Now let's look at the
build the Gradle files. In the dynamic module,
you can see a new Gradle plugin being used called Come
and Read Dynamic Feature. You also have to
add the base module as a dependency of
this dynamic module to access functionality
from the base module. Looking at the build Gradle
from the base module, the only change is to
declare all dynamic modules. This is to instruct
Gradle to make the resources stored in the
base module available to them. Now that we've created
our on-demand modules, let's write the code
to download them. In order to interact
with the Play Store to request these
on-demand modules, we have to use the split
install API, which is part of the Play core library. This is a Java clone
library that communicates with the Play Store via IPC. The Play Store IPC then
communicate with Play servers. The API is structured using
the same task framework that you may be familiar
with from Google Play services and Firebase APIs. Installation of
splits is coordinated by the Split Install Manager. You construct a request
with all the modules that you wish to
download, and then invoke Start Install to trigger
the Play Store to download and install the splits required
for the requested modules. For large modules, you'll need
to obtain the user confirmation prior to the download via
the Split Install API. You'll need to do this
whenever an app requests more than 10 megabytes
of on-demand modules to be downloaded. The API allows you to listen for
updates throughout the download and install process and
display this progress-- to allow to display
this progress to users. Here, we show the
download progress bar. An alternative option
for installing modules that aren't required
immediately is to use the deferred
installation API. These will be installed at a
convenient time for the user, generally when they
aren't using the device and are on Wi-Fi and charging. And because of this, we allow
you to install larger modules-- up to 100 megabytes-- without requiring
user confirmation. The Split Install
API also allows you to manage your
on-demand modules. You can see which
modules are installed. And you can choose to
uninstall modules that are no longer required by the app. This will free up precious
disk space for your users. So when installing an
on-demand module on N+ devices, the app does not
need to be restarted. Code is available immediately,
and new resources and assets are available once you
refresh the context object. However, on Android L
and M, installing splits requires the app
to fully restart. To avoid this, we include
a split compact library, which emulates the installation
of splits on L and M until the app goes
into the background and we can properly install it. If you are familiar with the
multidex support library, you will set up split compact
in a very similar way. Let's have a look. You have three options
to install split compact. You can use the split compact
application as your default application, or if you
already have an application, you can simply extend it. And if none of these
options suits you, then you can still also choose
to override the attach base context in your application
and invoke splitcomact.install. Now, let's talk
about versioning. When you release an
update to your app, Play will automatically
update both the base module and any on-demand modules
that are already installed. So the version of your
modules are always in sync. Partners tell us this
is something they really like about this model. PHIL ADAMS: Let's now talk
about the final step here-- helping users update to the
latest and greatest version of your app. You know that Play offers
auto update functionality. And many users do have
auto update turned on, but not all of them. And in some markets, it's
not uncommon for users to have auto updates turned
on, but for the device not to meet the requirements for
the auto update to take place. For example, they may
not connect to Wi-Fi. I'm happy to share that we're
launching a new API that helps you prompt users to update
without ever leaving your app. You can call this API
to determine, first, if there's an update available. And then if so, you can
show a prompt to your users so that they can update the app. In this example,
the flow is designed for immediate, critical use
cases, such as user privacy or revenue-affecting bugs. It's a full-screen
experience, where the user is expected to wait
for the update to be applied. It's an easy one for
you, the developer, to implement
because we take care of restarting the app for you. Some of you have built
similar flows for yourselves, but this is a
standardized method that you can use with
very little effort. Instead of that
immediate update, you can also put together
a flexible update, which does not have to
be applied straight away. The really cool
thing about this API is that you can completely
customize the update flow so that it feels
like part of your app. For example, you
may choose to nudge users to update
with an inline flow, like Google Chrome is
doing in this example. Once the user
accepts the update, the download happens
in the background, so the user can
keep using the app. And once the update
is complete, it's up to you and your app to
decide how to prompt the user to restart, or you
can simply wait until the app goes
into the background or is closed by the user. Google Chrome is
testing this now, and we're inviting
early access partners to start testing
this with us as well. Talk to your BD manager
if you're interested. Let's take a look
at the code that allows that flexible
in-app update to work. First, you can request an
instance of App Update Manager and then request
the app update info. This result is going to contain
the update availability status. If an update is available,
and the update is allowed, the return to app
update info object also contains an intent
to start the flow. If the app is allowed
to start, then you extract this pending
intent, and you start it. This will start the
download and installation. You can monitor the
state of an update by registering a listener
for status updates. When the download
is complete, you can choose again to install
it directly or defer the installation to a
more convenient time, for example using a snack bar. The restart happens when
complete update is called. So to recap this new
API, ensuring your users get the latest
update is important. And you can make that happen
by following some of these best practices up here on
the screen, and also by integrating with our
brand-new in-app updates API. The API is available
for any app, and so you can get
started with it in parallel to switching
to the Android App Bundle. PIERRE LECESNE: And that's it. We've now covered how
to make your app smaller and create dynamic features
using the Android App Bundle, and how you can ensure
that your users stay on the latest
version of your app using the new in
app updates API. If you want to come and
chat about any of this, you can find us at the
office hours or the demos on the Google Play stand
today and tomorrow. Also, if you want to share
about what we've talked today with your team, the
medium post at this link is a great place to start. Enjoy the rest of your day. Thank you. [MUSIC PLAYING]