Skip to content

Instantly share code, notes, and snippets.

@axeldelafosse
Last active October 12, 2023 19:57
Show Gist options
  • Save axeldelafosse/8cd7274501180257ae4951a0dc8759c2 to your computer and use it in GitHub Desktop.
Save axeldelafosse/8cd7274501180257ae4951a0dc8759c2 to your computer and use it in GitHub Desktop.
[DEPRECATED] React Native MMKV - Config plugin for Expo. You need to use "react-native-mmkv": "^1.6.2"
// DEPRECATED
const {
withDangerousMod,
WarningAggregator,
AndroidConfig,
withAppBuildGradle,
} = require("@expo/config-plugins");
const path = require("path");
const fs = require("fs");
function getMMKVJSIModulePackage(packageName) {
return `package ${packageName};
import com.facebook.react.bridge.JSIModuleSpec;
import com.facebook.react.bridge.JavaScriptContextHolder;
import com.facebook.react.bridge.ReactApplicationContext;
import com.swmansion.reanimated.ReanimatedJSIModulePackage;
import com.reactnativemmkv.MmkvModule;
import java.util.Collections;
import java.util.List;
public class MMKVJSIModulePackage extends ReanimatedJSIModulePackage {
@Override
public List<JSIModuleSpec> getJSIModules(ReactApplicationContext reactApplicationContext, JavaScriptContextHolder jsContext) {
MmkvModule.install(jsContext, reactApplicationContext.getFilesDir().getAbsolutePath() + "/mmkv");
return super.getJSIModules(reactApplicationContext, jsContext);
}
}`;
}
async function readFileAsync(path) {
return fs.promises.readFile(path, "utf8");
}
async function saveFileAsync(path, content) {
return fs.promises.writeFile(path, content, "utf8");
}
function getPackageRoot(projectRoot) {
return path.join(projectRoot, "android", "app", "src", "main", "java");
}
function getCurrentPackageName(projectRoot, packageRoot) {
const mainApplication = AndroidConfig.Paths.getProjectFilePath(
projectRoot,
"MainApplication"
);
const packagePath = path.dirname(mainApplication);
const packagePathParts = path
.relative(packageRoot, packagePath)
.split(path.sep)
.filter(Boolean);
return packagePathParts.join(".");
}
async function editMainApplication(config, action) {
const mainApplicationPath = AndroidConfig.Paths.getProjectFilePath(
config.modRequest.projectRoot,
"MainApplication"
);
try {
const mainApplication = action(await readFileAsync(mainApplicationPath));
return await saveFileAsync(mainApplicationPath, mainApplication);
} catch (e) {
WarningAggregator.addWarningAndroid(
"react-native-mmkv",
`Couldn't modify MainApplication.java - ${e}.`
);
}
}
async function createMMKVJSIModulePackage(config, action) {
const projectRoot = config.modRequest.projectRoot;
const packageRoot = getPackageRoot(projectRoot);
const packageName = getCurrentPackageName(projectRoot, packageRoot);
const filePath = path.join(
packageRoot,
`${packageName.split(".").join("/")}/MMKVJSIModulePackage.java`
);
try {
return await saveFileAsync(filePath, getMMKVJSIModulePackage(packageName));
} catch (e) {
WarningAggregator.addWarningAndroid(
"react-native-mmkv",
`Couldn't create MMKVJSIModulePackage.java - ${e}.`
);
}
}
const withMMKVJSIModulePackage = (config) => {
return withDangerousMod(config, [
"android",
async (config) => {
await createMMKVJSIModulePackage(config);
return config;
},
]);
};
const withMainApplication = (config) => {
return withDangerousMod(config, [
"android",
async (config) => {
await editMainApplication(config, (mainApplication) => {
if (mainApplication.includes('return new MMKVJSIModulePackage();')) {
return mainApplication;
}
mainApplication = mainApplication.replace(
` @Override
protected String getJSMainModuleName() {
return "index";
}`,
` @Override
protected String getJSMainModuleName() {
return "index";
}
@Override
protected JSIModulePackage getJSIModulePackage() {
return new MMKVJSIModulePackage();
}`
);
return mainApplication;
});
return config;
},
]);
};
const withCustomAppBuildGradle = (config) => {
return withAppBuildGradle(config, (config) => {
if (
config.modResults.contents.includes(
`implementation project(':react-native-mmkv')`
)
) {
return config;
}
config.modResults.contents = config.modResults.contents.replace(
`implementation "com.facebook.react:react-native:+" // From node_modules`,
`implementation "com.facebook.react:react-native:+" // From node_modules
implementation project(':react-native-mmkv')`
);
return config;
});
};
module.exports = function withMMKV(config) {
config = withMMKVJSIModulePackage(config);
config = withMainApplication(config);
config = withCustomAppBuildGradle(config);
return config;
};
@mgscreativa
Copy link

Thanks @hirbod ! Yes, actually I'm using custom dev client, so will test it out. Thanks!

@Laviniaxyz
Copy link

Hello,
Can someone share their latest, functional react-native-mmkv-plugin file? I have tried using the shared plugin, but I get the same error: "Failed to create new MMKV instance...etc".
I use expo sdk 44.0.0 & react-native-mmkv 1.6.2. I have also added the plugin in my app.json file: "plugins": [ "./react-native-mmkv-plugin.js" ]

Are you using the EAS build? Did you rebuild the dev client?

No, I was hoping to use this library in an expo managed environment, but from what I see it is not supported.

@hirbod
Copy link

hirbod commented Aug 29, 2022

@Laviniaxyz this library adds native code, so using the managed env is indeed not possible. But creating a custom dev client with Xcode/Studio or EAS is actually straightforward and like 10 minutes of effort.

@samrith-s
Copy link

Does this work with Expo SDK 47?

@hirbod
Copy link

hirbod commented Nov 19, 2022

There is no need for this plug-in anymore. It works ootb with a dev client

@samrith-s
Copy link

Ok, do I still need to run expo prebuild?

@hirbod
Copy link

hirbod commented Nov 21, 2022

Yes

@mariomurrent-softwaresolutions

Is this still valid? Seems to be broken in SDK 48

@hirbod
Copy link

hirbod commented Feb 13, 2023

Still valid. You need to make sure to update mmkv for RN 0.71

@mariomurrent-softwaresolutions
Copy link

mariomurrent-softwaresolutions commented Feb 13, 2023

@hirbod I upgraded mmkv to 2.7.1 but this did not help either

@simon-ojok
Copy link

@axeldelafosse How about if you create npm page that we can install intead of us copying these codes

@nandorojo
Copy link

@simon-ojok he provided this for free, you’re welcome to do that yourself if you want.

but also this is deprecated and isn’t needed anymore

@biratdevpoudel
Copy link

There is no need for this plug-in anymore. It works ootb with a dev client

yes worked for me aswell

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment