A common problem we face is the protection of out private data such as API keys.
When working with Flutter, you may need to integrate a third party service which requires you to add your API key to your manifest file.
You wouldn't want to check-in your API keys to the source code. Instead, you would like to embed them into an internal file ignored by your source control and use them through your app. For Android there's already a standard file that's used for this purpose called local.properties.
The AndroidManifest.xml is an xml file thus we cannot write scripts there. Instead, we can write a small script in build.gradle file, read api key from the local.properties file and assign it to a variable. AndroidManifest will be able to read that variable.
Let's dive into the code!
Assuming we want to integrate segment, we would need to add the write key toe our AndroidManifest.xml file, instead of writing the clear API key, we would write :
<meta-data android:name="com.claimsforce.segment.WRITE_KEY" android:value="${segmentWriteKey}" />
And then register the API Key in the local.properties
file under the variable named "segment.writeKey" like:
sdk.dir=
flutter.sdk=
flutter.buildMode=debug
flutter.versionName=1.0.0
flutter.versionCode=1
segment.writeKey=<SEGMENT API KEY GOES HERE> # We've added this line
segmentWriteKey
is the name of the variable we are going to create in the module level build.gradle (android/app/build.gradle).
Add these lines before android{} :
Properties properties = new Properties()
properties.load(project.rootProject.file('local.properties').newDataInputStream())
def segmentWriteKey = properties.getProperty('segment.writeKey') // Notice we get the property we the exact same name we wrote in the local.properties file
This should look like :
Properties properties = new Properties()
properties.load(project.rootProject.file('local.properties').newDataInputStream())
def segmentWriteKey = properties.getProperty('segment.writeKey')
android {
compileSdkVersion 28
...
}
Under the android section, in the defaultConfig, add this line to the end:
manifestPlaceholders = [segmentWriteKey: segmentWriteKey]
Now everything should look like:
Properties properties = new Properties()
properties.load(project.rootProject.file('local.properties').newDataInputStream())
def segmentWriteKey = properties.getProperty('segment.writeKey')
android {
...
defaultConfig {
...
manifestPlaceholders = [segmentWriteKey: segmentWriteKey]
}
...
}
Note that the local.properties file is ignore by the source control by default so you will not have to do it yourself (but prevention is better than cure ;) ).
Well, we are done.
Hope this article helped you and see you on another one.
Thanks for reading.
Top comments (7)
Good job! It works for me.
How to delare it in yml so that github actions run properly?
You can add a step in your build job like this :
how to access this key in the app??
You will need to write plateform channels to do that.
Since we've declared a variable in our gradle, it will be avaible for use in Java/Kotlin under the
BuildConfig
class.how about the iOS?
These variables on iOS side are generally used in the AppDelegate class. It's then easy for you as a developer to hide their values: