Tinker patches your Android APK, and Google Play forbids exactly that
Tinker is a hot-fix solution library for Android, it supports dex, library and resources update without reinstall apk.
At a glance
- What is it?
- Tencent's Tinker swaps dex, library and resource changes into a running Android app without a reinstall, at the cost of rewriting your Application class and losing Google Play as a distribution channel. The English setup instructions stop at version 1.9.1 while the newest tag is v1.9.15.2.
- Who is it for?
- Tinker fits an enterprise app pushed through a device manager or sideloaded onto devices you control, where a patched build has to reach hardware you are responsible for. It does not fit a Play-distributed consumer app, because the project's own known-issues list names the Google Play Developer Distribution Agreement as the reason it cannot update your apk, and adding an Android component still needs a real install.
- Can I use it commercially?
- Check first. The repository uses a licence we do not classify automatically, so read its LICENSE file before any commercial use.
- Is it still maintained?
- Yes. The repository last received commits 22 days ago.
- What is it written in?
- Mainly Java, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on November 14, 2026, and from our analysis. They are not legal advice.
Star history
- Tencent/tinker17,663 ★ · +14
| Repository | 2026-09-21 | 2026-11-14 |
|---|---|---|
| Tencent/tinker | 17.6k | 17.7k |
14 Stars in the last 54 days, measured from the daily GitHub snapshot. Compare with other projects
Editorial analysis
Google Play terms rule it out, and AndroidManifest.xml is off limits
Three limits are stated in the README's known issues section, and the first one decides who this library is for. Due to the Google Play Developer Distribution Agreement, we can't dynamic update our apk. That is not a missing feature pending a patch release, it is a distribution constraint, and it means every app installed from the Play Store is out of scope. The audience is an app you push through a device manager, an MDM, or sideloading onto devices you administer.
The second limit is architectural rather than legal. Tinker can't update AndroidManifest.xml, such as add Android component. A new Activity, a BroadcastReceiver, a Service, a permission or a provider is declared in that file, so the set of components your app can ever have is frozen at install time. Hot patching a bug in an existing screen works. Shipping a feature that needs a new component does not, and the fix is a release, not a patch.
The third is narrow and worth quoting exactly because it is the kind of thing that wastes an afternoon: Tinker does not support some Samsung models with os version android-21. If your fleet includes those handsets, no amount of configuration changes it.
TinkerApplication has no default constructor, so the lifecycle class travels as a string
The mechanism that makes a hot patch loadable is a deliberate break in the type system. TinkerApplication is an abstract class with no default constructor, so your Application class has to define a no-arg one and hand two things up: a flag saying which update types are supported, and the fully qualified name of your lifecycle class, passed as a string so the shell application does not have a binary dependency on your ApplicationLifeCycle class.
public class SampleApplication extends TinkerApplication {
public SampleApplication() {
super(
//tinkerFlags, which types is supported
//dex only, library only, all support
ShareConstants.TINKER_ENABLE_ALL,
// This is passed as a string so the shell application does not
// have a binary dependency on your ApplicationLifeCycle class.
"tinker.sample.android.app.SampleApplicationLike");
}
}That string is the price of the design, and it is worth understanding before you rely on it. A wrong class name is not a compile error, because there is no type to check it against. It becomes a class-not-found at patch-load time, on a device, after a release has already shipped. The alternative path avoids the hand-written constructor: add tinker-android-anno, annotate the lifecycle class with @DefaultLifeCycle carrying the application name and the same flags, and tinker-android-anno generates the Application class for you.
The setup page pins 1.9.1 and the newest tag is v1.9.15.2
Every version string in the getting started section is 1.9.1: the gradle plugin classpath, the optional tinker-android-anno artifact and tinker-android-lib. The release list tells a different story. v1.9.15.2 was tagged on 2025-07-07, and v1.9.15 and v1.9.15.1 were both tagged on 2024-12-09. So the documented coordinates are well behind the newest tag, and the English page has not been updated to close that gap.
The repository itself is not archived and the last push is dated 2026-10-23, so the code is being worked on well past the newest release. Work on a branch and a published tag that far apart is normal, and it is also a thing to ask about: if you take 1.9.1 because the page says so, you are not taking the version the project is actually working on.
One more navigational detail. The default branch of this repository is dev, while every GitHub link inside the README points at master, including the LICENSE link and the sample project links. A link pasted from that page will land on whatever master is, and on a repository whose default is dev those are two different trees. Read the source rather than trusting the deep links.
The Ark path is half finished and hands you an unsigned patch
Ark support is the newest thing described and the least complete. Building a patch is a single script that takes the absolute paths of two apks, the one with bugs and the one with the fix, neither compiled by Ark:
bash build_patch_dexdiff.sh old=xxx new=xxxThe configuration side is written out for both front ends. For tinker-cli you add an issue entry to tinker_config.xml with a path of arkHot and a name of patch.apk. For gradle you add an ark block with the same two values to app/build.gradle. Without either, the default configuration applies. The finished patch apk contains two files: classes.dex for Android, and patch.apk holding the shared object for Ark.
What is missing is the middle. The heading for compiling in Ark is followed by the single word TODO, and the next line says it is at present compiled by the Ark compiler team, with the output patch still packaged in APK format without signature. So this path depends on a separate team producing the artefact, and what comes back is unsigned. If your delivery process signs every artefact, that step is now yours, on a path the project describes as provisional.
The plugin writes your ProGuard rules and the multidex keep file for you
One line in the README saves the most tedious part of a hot-patch integration. For proguard, the project has already made the proguard config automatic, and Tinker will also generate the multidex keep proguard file for you. You are not hand-maintaining a keep list for the loader classes, which is the step that quietly breaks a shrunk release build when it is wrong.
The flip side is that your effective ProGuard configuration is no longer readable from your own build files. The plugin contributes rules you cannot see in build.gradle, so when a release build fails on a missing class at patch-load time, the first place to look is not your own config. Diff the effective configuration before you start bisecting your own code.
The rest of the build glue is conventional. The plugin artifact goes on the buildscript classpath, the Android library goes into the app module, and the plugin is applied by id. Both dependency lines in the sample use the provided and compile configuration names rather than implementation, which is the first thing to reconcile with a build that has moved on.
The Application class has to be restructured before anything else works
Adopting Tinker is not adding a dependency. The README is explicit that if your app has a class that subclasses android.app.Application, you have to modify that class and move all its implements to a SampleApplicationLike rather than Application. In the sample diff that is the whole change: the class stops extending Application and starts extending DefaultApplicationLike.
-public class YourApplication extends Application {
+public class SampleApplicationLike extends DefaultApplicationLike {After that, your Application class becomes a subclass of TinkerApplication. So the base class of your app's entry point is now someone else's, permanently, and every library that reflects over your Application, every test that constructs one, and every manifest reference has to line up with a shape you did not choose. None of that is reversible by removing the dependency later without restoring the original class.
This is the part to plan for. Budget a day for the restructure and a release that carries the loader, and do not attempt to introduce a patch pipeline into an app whose release train is already fixed.
The support path after the README is a Chinese wiki and a Chinese FAQ
The Tinker support section gives four places to go: the tinker-sample-android project, the source code, the wiki or FAQ, and contacting the team. The first two are language-neutral. The other two are not. The README links its own description as 中文说明, pointing at the wiki, and the FAQ link resolves to a page named 常见问题, which is Chinese for frequently asked questions.
So the English README is the entire English documentation, and it ends at the flag names, the Ark XML block and the three known issues. For more configuration the README points to the sample app/build.gradle, and beyond that to a wiki you have to be able to read.
The licence story is thin in the same way. The README says Tinker is under the BSD licence and links the LICENSE file, and that sentence is the only statement of terms in the project text, while no licence identifier at all appears in the repository metadata. If your compliance process needs a licence it can read from a package manager rather than a link in a README, that is a step to take before you vendor it.
Editorial conclusion
Tinker fits an enterprise app pushed through a device manager or sideloaded onto devices you control, where a patched build has to reach hardware you are responsible for. It does not fit a Play-distributed consumer app, because the project's own known-issues list names the Google Play Developer Distribution Agreement as the reason it cannot update your apk, and adding an Android component still needs a real install. Before you commit, check the version you would actually depend on: every coordinate in the setup instructions is pinned at 1.9.1, the newest tag is v1.9.15.2 from 2025-07-07, and the default branch is dev while the README's own links point at master.
Frequently asked questions
Can Tencent Tinker update an app that is distributed through Google Play?
No. The known issues section states that, due to the Google Play Developer Distribution Agreement, Tinker cannot dynamic update your apk. The same list says AndroidManifest.xml cannot be updated, so adding an Android component still requires a full install.
What can Tinker patch on Android, and what does it refuse to touch?
It supports dex, library and resource updates without reinstalling the apk, with flags for dex only, library only or all, and the sample passes ShareConstants.TINKER_ENABLE_ALL. It cannot update AndroidManifest.xml, and it does not support some Samsung models with os version android-21.
How do I set up Tinker in an Android project?
Add com.tencent.tinker:tinker-patch-gradle-plugin to the buildscript classpath, then add tinker-android-anno and tinker-android-lib to app/build.gradle and apply plugin: 'com.tencent.tinker.patch'. Your Application class must extend TinkerApplication with a no-arg constructor that passes a tinker flag and the lifecycle class name as a string.
Which licence does Tinker use?
The README states that Tinker is under the BSD licence and links to the LICENSE file. That sentence is the only statement of terms in the project text, and no licence identifier appears in the repository metadata.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/tencent-tinker)Star history chart for your README
[](https://hysenlabs.com/projects/tencent-tinker)Was this useful?