mirror of
https://github.com/revanced/revanced-manager.git
synced 2025-06-13 04:57:37 +02:00
build(Needs bump): Bump ReVanced Patcher (#2242)
Co-authored-by: aAbed <aabedhkhan@gmail.com>
This commit is contained in:
@ -111,11 +111,7 @@ class GithubAPI {
|
||||
);
|
||||
if (asset != null) {
|
||||
final String downloadUrl = asset['browser_download_url'];
|
||||
if (extension == '.apk') {
|
||||
_managerAPI.setIntegrationsDownloadURL(downloadUrl);
|
||||
} else {
|
||||
_managerAPI.setPatchesDownloadURL(downloadUrl);
|
||||
}
|
||||
_managerAPI.setPatchesDownloadURL(downloadUrl);
|
||||
return await _downloadManager.getSingleFile(
|
||||
downloadUrl,
|
||||
);
|
||||
|
@ -44,15 +44,13 @@ class ManagerAPI {
|
||||
String keystoreFile =
|
||||
'/sdcard/Android/data/app.revanced.manager.flutter/files/revanced-manager.keystore';
|
||||
String defaultKeystorePassword = 's3cur3p@ssw0rd';
|
||||
String defaultApiUrl = 'https://api.revanced.app/';
|
||||
String defaultApiUrl = 'https://api.revanced.app/v3';
|
||||
String defaultRepoUrl = 'https://api.github.com';
|
||||
String defaultPatcherRepo = 'revanced/revanced-patcher';
|
||||
String defaultPatchesRepo = 'revanced/revanced-patches';
|
||||
String defaultIntegrationsRepo = 'revanced/revanced-integrations';
|
||||
String defaultCliRepo = 'revanced/revanced-cli';
|
||||
String defaultManagerRepo = 'revanced/revanced-manager';
|
||||
String? patchesVersion = '';
|
||||
String? integrationsVersion = '';
|
||||
|
||||
Future<void> initialize() async {
|
||||
_prefs = await SharedPreferences.getInstance();
|
||||
@ -69,13 +67,15 @@ class ManagerAPI {
|
||||
}
|
||||
|
||||
// Migrate to new API URL if not done yet as the old one is sunset.
|
||||
final bool hasMigratedToNewApi =
|
||||
_prefs.getBool('migratedToNewApiUrl') ?? false;
|
||||
if (!hasMigratedToNewApi) {
|
||||
final bool hasMigratedToLatestApi =
|
||||
_prefs.getBool('migratedToLatestApiUrl') ?? false;
|
||||
if (!hasMigratedToLatestApi) {
|
||||
final String apiUrl = getApiUrl().toLowerCase();
|
||||
if (apiUrl.contains('releases.revanced.app')) {
|
||||
if (apiUrl.contains('releases.revanced.app') ||
|
||||
(apiUrl.contains('api.revanced.app') &&
|
||||
!apiUrl.contains('v3'))) {
|
||||
await setApiUrl(''); // Reset to default.
|
||||
_prefs.setBool('migratedToNewApiUrl', true);
|
||||
_prefs.setBool('migratedToLatestApiUrl', true);
|
||||
}
|
||||
}
|
||||
|
||||
@ -83,10 +83,8 @@ class ManagerAPI {
|
||||
_prefs.getBool('migratedToAlternativeSource') ?? false;
|
||||
if (!hasMigratedToAlternativeSource) {
|
||||
final String patchesRepo = getPatchesRepo();
|
||||
final String integrationsRepo = getIntegrationsRepo();
|
||||
final bool usingAlternativeSources =
|
||||
patchesRepo.toLowerCase() != defaultPatchesRepo ||
|
||||
integrationsRepo.toLowerCase() != defaultIntegrationsRepo;
|
||||
patchesRepo.toLowerCase() != defaultPatchesRepo;
|
||||
_prefs.setBool('useAlternativeSources', usingAlternativeSources);
|
||||
_prefs.setBool('migratedToAlternativeSource', true);
|
||||
}
|
||||
@ -200,14 +198,6 @@ class ManagerAPI {
|
||||
await _prefs.setStringList('savedPatches-$packageName', patchesJson);
|
||||
}
|
||||
|
||||
String getIntegrationsDownloadURL() {
|
||||
return _prefs.getString('integrationsDownloadURL') ?? '';
|
||||
}
|
||||
|
||||
Future<void> setIntegrationsDownloadURL(String value) async {
|
||||
await _prefs.setString('integrationsDownloadURL', value);
|
||||
}
|
||||
|
||||
List<Patch> getUsedPatches(String packageName) {
|
||||
final List<String> patchesJson =
|
||||
_prefs.getStringList('usedPatches-$packageName') ?? [];
|
||||
@ -256,17 +246,6 @@ class ManagerAPI {
|
||||
_prefs.remove('patchOption-$packageName-$patchName-$key');
|
||||
}
|
||||
|
||||
String getIntegrationsRepo() {
|
||||
return _prefs.getString('integrationsRepo') ?? defaultIntegrationsRepo;
|
||||
}
|
||||
|
||||
Future<void> setIntegrationsRepo(String value) async {
|
||||
if (value.isEmpty || value.startsWith('/') || value.endsWith('/')) {
|
||||
value = defaultIntegrationsRepo;
|
||||
}
|
||||
await _prefs.setString('integrationsRepo', value);
|
||||
}
|
||||
|
||||
bool getUseDynamicTheme() {
|
||||
return _prefs.getBool('useDynamicTheme') ?? false;
|
||||
}
|
||||
@ -464,28 +443,7 @@ class ManagerAPI {
|
||||
final String currentVersion = await getCurrentPatchesVersion();
|
||||
final String url = getPatchesDownloadURL();
|
||||
return await _githubAPI.getReleaseFile(
|
||||
'.jar',
|
||||
repoName,
|
||||
currentVersion,
|
||||
url,
|
||||
);
|
||||
} on Exception catch (e) {
|
||||
if (kDebugMode) {
|
||||
print(e);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
Future<File?> downloadIntegrations() async {
|
||||
try {
|
||||
final String repoName = !isUsingAlternativeSources()
|
||||
? defaultIntegrationsRepo
|
||||
: getIntegrationsRepo();
|
||||
final String currentVersion = await getCurrentIntegrationsVersion();
|
||||
final String url = getIntegrationsDownloadURL();
|
||||
return await _githubAPI.getReleaseFile(
|
||||
'.apk',
|
||||
'.rvp',
|
||||
repoName,
|
||||
currentVersion,
|
||||
url,
|
||||
@ -499,18 +457,12 @@ class ManagerAPI {
|
||||
}
|
||||
|
||||
Future<File?> downloadManager() async {
|
||||
return await _revancedAPI.getLatestReleaseFile(
|
||||
'.apk',
|
||||
defaultManagerRepo,
|
||||
);
|
||||
return await _revancedAPI.getLatestReleaseFile('manager');
|
||||
}
|
||||
|
||||
Future<String?> getLatestPatchesReleaseTime() async {
|
||||
if (!isUsingAlternativeSources()) {
|
||||
return await _revancedAPI.getLatestReleaseTime(
|
||||
'.json',
|
||||
defaultPatchesRepo,
|
||||
);
|
||||
return await _revancedAPI.getLatestReleaseTime('patches');
|
||||
} else {
|
||||
final release = await _githubAPI.getLatestRelease(getPatchesRepo());
|
||||
if (release != null) {
|
||||
@ -525,39 +477,20 @@ class ManagerAPI {
|
||||
|
||||
Future<String?> getLatestManagerReleaseTime() async {
|
||||
return await _revancedAPI.getLatestReleaseTime(
|
||||
'.apk',
|
||||
defaultManagerRepo,
|
||||
'manager',
|
||||
);
|
||||
}
|
||||
|
||||
Future<String?> getLatestManagerVersion() async {
|
||||
return await _revancedAPI.getLatestReleaseVersion(
|
||||
'.apk',
|
||||
defaultManagerRepo,
|
||||
'manager',
|
||||
);
|
||||
}
|
||||
|
||||
Future<String?> getLatestIntegrationsVersion() async {
|
||||
if (!isUsingAlternativeSources()) {
|
||||
return await _revancedAPI.getLatestReleaseVersion(
|
||||
'.apk',
|
||||
defaultIntegrationsRepo,
|
||||
);
|
||||
} else {
|
||||
final release = await _githubAPI.getLatestRelease(getIntegrationsRepo());
|
||||
if (release != null) {
|
||||
return release['tag_name'];
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Future<String?> getLatestPatchesVersion() async {
|
||||
if (!isUsingAlternativeSources()) {
|
||||
return await _revancedAPI.getLatestReleaseVersion(
|
||||
'.json',
|
||||
defaultPatchesRepo,
|
||||
'patches',
|
||||
);
|
||||
} else {
|
||||
final release = await _githubAPI.getLatestRelease(getPatchesRepo());
|
||||
@ -620,25 +553,6 @@ class ManagerAPI {
|
||||
await downloadPatches();
|
||||
}
|
||||
|
||||
Future<String> getCurrentIntegrationsVersion() async {
|
||||
integrationsVersion = _prefs.getString('integrationsVersion') ?? '0.0.0';
|
||||
if (integrationsVersion == '0.0.0' || isPatchesAutoUpdate()) {
|
||||
final String newIntegrationsVersion =
|
||||
await getLatestIntegrationsVersion() ?? '0.0.0';
|
||||
if (integrationsVersion != newIntegrationsVersion &&
|
||||
newIntegrationsVersion != '0.0.0') {
|
||||
await setCurrentIntegrationsVersion(newIntegrationsVersion);
|
||||
}
|
||||
}
|
||||
return integrationsVersion!;
|
||||
}
|
||||
|
||||
Future<void> setCurrentIntegrationsVersion(String version) async {
|
||||
await _prefs.setString('integrationsVersion', version);
|
||||
await setIntegrationsDownloadURL('');
|
||||
await downloadIntegrations();
|
||||
}
|
||||
|
||||
Future<List<PatchedApplication>> getAppsToRemove(
|
||||
List<PatchedApplication> patchedApps,
|
||||
) async {
|
||||
|
@ -33,7 +33,6 @@ class PatcherAPI {
|
||||
|
||||
Future<void> initialize() async {
|
||||
await loadPatches();
|
||||
await _managerAPI.downloadIntegrations();
|
||||
final Directory appCache = await getApplicationSupportDirectory();
|
||||
_dataDir = await getExternalStorageDirectory() ?? appCache;
|
||||
_tmpDir = Directory('${appCache.path}/patcher');
|
||||
@ -153,7 +152,6 @@ class PatcherAPI {
|
||||
List<Patch> selectedPatches,
|
||||
bool isFromStorage,
|
||||
) async {
|
||||
final File? integrationsFile = await _managerAPI.downloadIntegrations();
|
||||
final Map<String, Map<String, dynamic>> options = {};
|
||||
for (final patch in selectedPatches) {
|
||||
if (patch.options.isNotEmpty) {
|
||||
@ -169,44 +167,41 @@ class PatcherAPI {
|
||||
}
|
||||
}
|
||||
|
||||
if (integrationsFile != null) {
|
||||
_dataDir.createSync();
|
||||
_tmpDir.createSync();
|
||||
final Directory workDir = await _tmpDir.createTemp('tmp-');
|
||||
_dataDir.createSync();
|
||||
_tmpDir.createSync();
|
||||
final Directory workDir = await _tmpDir.createTemp('tmp-');
|
||||
|
||||
final File inApkFile = File('${workDir.path}/in.apk');
|
||||
await File(apkFilePath).copy(inApkFile.path);
|
||||
final File inApkFile = File('${workDir.path}/in.apk');
|
||||
await File(apkFilePath).copy(inApkFile.path);
|
||||
|
||||
if (isFromStorage) {
|
||||
// The selected apk was copied to cacheDir by the file picker, so it's not needed anymore.
|
||||
// rename() can't be used here, as Android system also counts the size of files moved out from cacheDir
|
||||
// as part of the app's cache size.
|
||||
File(apkFilePath).delete();
|
||||
}
|
||||
if (isFromStorage) {
|
||||
// The selected apk was copied to cacheDir by the file picker, so it's not needed anymore.
|
||||
// rename() can't be used here, as Android system also counts the size of files moved out from cacheDir
|
||||
// as part of the app's cache size.
|
||||
File(apkFilePath).delete();
|
||||
}
|
||||
|
||||
outFile = File('${workDir.path}/out.apk');
|
||||
outFile = File('${workDir.path}/out.apk');
|
||||
|
||||
final Directory tmpDir =
|
||||
Directory('${workDir.path}/revanced-temporary-files');
|
||||
final Directory tmpDir =
|
||||
Directory('${workDir.path}/revanced-temporary-files');
|
||||
|
||||
try {
|
||||
await patcherChannel.invokeMethod(
|
||||
'runPatcher',
|
||||
{
|
||||
'inFilePath': inApkFile.path,
|
||||
'outFilePath': outFile!.path,
|
||||
'integrationsPath': integrationsFile.path,
|
||||
'selectedPatches': selectedPatches.map((p) => p.name).toList(),
|
||||
'options': options,
|
||||
'tmpDirPath': tmpDir.path,
|
||||
'keyStoreFilePath': _keyStoreFile.path,
|
||||
'keystorePassword': _managerAPI.getKeystorePassword(),
|
||||
},
|
||||
);
|
||||
} on Exception catch (e) {
|
||||
if (kDebugMode) {
|
||||
print(e);
|
||||
}
|
||||
try {
|
||||
await patcherChannel.invokeMethod(
|
||||
'runPatcher',
|
||||
{
|
||||
'inFilePath': inApkFile.path,
|
||||
'outFilePath': outFile!.path,
|
||||
'selectedPatches': selectedPatches.map((p) => p.name).toList(),
|
||||
'options': options,
|
||||
'tmpDirPath': tmpDir.path,
|
||||
'keyStoreFilePath': _keyStoreFile.path,
|
||||
'keystorePassword': _managerAPI.getKeystorePassword(),
|
||||
},
|
||||
);
|
||||
} on Exception catch (e) {
|
||||
if (kDebugMode) {
|
||||
print(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,7 +1,5 @@
|
||||
import 'dart:async';
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:collection/collection.dart';
|
||||
import 'package:dio/dio.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:flutter_cache_manager/flutter_cache_manager.dart';
|
||||
@ -31,7 +29,7 @@ class RevancedAPI {
|
||||
final Map<String, List<dynamic>> contributors = {};
|
||||
try {
|
||||
final response = await _dio.get('/contributors');
|
||||
final List<dynamic> repositories = response.data['repositories'];
|
||||
final List<dynamic> repositories = response.data;
|
||||
for (final Map<String, dynamic> repo in repositories) {
|
||||
final String name = repo['name'];
|
||||
contributors[name] = repo['contributors'];
|
||||
@ -46,21 +44,15 @@ class RevancedAPI {
|
||||
}
|
||||
|
||||
Future<Map<String, dynamic>?> _getLatestRelease(
|
||||
String extension,
|
||||
String repoName,
|
||||
String toolName,
|
||||
) {
|
||||
if (!locator<ManagerAPI>().getDownloadConsent()) {
|
||||
return Future(() => null);
|
||||
}
|
||||
return getToolsLock.synchronized(() async {
|
||||
try {
|
||||
final response = await _dio.get('/tools');
|
||||
final List<dynamic> tools = response.data['tools'];
|
||||
return tools.firstWhereOrNull(
|
||||
(t) =>
|
||||
(t['repository'] as String) == repoName &&
|
||||
(t['name'] as String).endsWith(extension),
|
||||
);
|
||||
final response = await _dio.get('/$toolName/latest');
|
||||
return response.data;
|
||||
} on Exception catch (e) {
|
||||
if (kDebugMode) {
|
||||
print(e);
|
||||
@ -71,13 +63,11 @@ class RevancedAPI {
|
||||
}
|
||||
|
||||
Future<String?> getLatestReleaseVersion(
|
||||
String extension,
|
||||
String repoName,
|
||||
String toolName,
|
||||
) async {
|
||||
try {
|
||||
final Map<String, dynamic>? release = await _getLatestRelease(
|
||||
extension,
|
||||
repoName,
|
||||
toolName,
|
||||
);
|
||||
if (release != null) {
|
||||
return release['version'];
|
||||
@ -92,16 +82,14 @@ class RevancedAPI {
|
||||
}
|
||||
|
||||
Future<File?> getLatestReleaseFile(
|
||||
String extension,
|
||||
String repoName,
|
||||
String toolName,
|
||||
) async {
|
||||
try {
|
||||
final Map<String, dynamic>? release = await _getLatestRelease(
|
||||
extension,
|
||||
repoName,
|
||||
toolName,
|
||||
);
|
||||
if (release != null) {
|
||||
final String url = release['browser_download_url'];
|
||||
final String url = release['assets'][0]['download_url'];
|
||||
return await _downloadManager.getSingleFile(url);
|
||||
}
|
||||
} on Exception catch (e) {
|
||||
@ -129,13 +117,10 @@ class RevancedAPI {
|
||||
}
|
||||
|
||||
Future<File?> downloadManager() async {
|
||||
final Map<String, dynamic>? release = await _getLatestRelease(
|
||||
'.apk',
|
||||
'revanced/revanced-manager',
|
||||
);
|
||||
final Map<String, dynamic>? release = await _getLatestRelease('manager');
|
||||
File? outputFile;
|
||||
await for (final result in _downloadManager.getFileStream(
|
||||
release!['browser_download_url'] as String,
|
||||
release!['download_url'] as String,
|
||||
)) {
|
||||
if (result is DownloadProgress) {
|
||||
final totalSize = result.totalSize ?? 10000000;
|
||||
@ -152,17 +137,15 @@ class RevancedAPI {
|
||||
}
|
||||
|
||||
Future<String?> getLatestReleaseTime(
|
||||
String extension,
|
||||
String repoName,
|
||||
String toolName,
|
||||
) async {
|
||||
try {
|
||||
final Map<String, dynamic>? release = await _getLatestRelease(
|
||||
extension,
|
||||
repoName,
|
||||
toolName,
|
||||
);
|
||||
if (release != null) {
|
||||
final DateTime timestamp =
|
||||
DateTime.parse(release['timestamp'] as String);
|
||||
DateTime.parse(release['created_at'] as String);
|
||||
return format(timestamp, locale: 'en_short');
|
||||
}
|
||||
} on Exception catch (e) {
|
||||
|
Reference in New Issue
Block a user