Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Inputs checks Backport to 1.19.4 #21

Merged
merged 9 commits into from
Mar 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import com.adamcalculator.dynamicpack.pack.Pack;
import com.adamcalculator.dynamicpack.pack.Remote;
import com.adamcalculator.dynamicpack.util.AFiles;
import com.adamcalculator.dynamicpack.util.FailedOpenPackFileSystemException;
import com.adamcalculator.dynamicpack.util.Out;
import org.json.JSONObject;

Expand All @@ -19,6 +20,7 @@ public abstract class DynamicPackModBase {
public static final String MINECRAFT_META = "pack.mcmeta";

public static DynamicPackModBase INSTANCE;
protected static int manuallySyncThreadCounter = 0;

private boolean isPacksScanning = false;
private List<Pack> packs = new ArrayList<>();
Expand All @@ -40,8 +42,13 @@ public void init(File gameDir) {
startSyncThread();
}

/**
* ONLY FOR FIRST INIT RUN! FOR MANUALLY USE startManuallySync!!!!!
*/
public abstract void startSyncThread();

public abstract void startManuallySync();

public void rescanPacks() {
if (isPacksScanning) {
Out.warn("rescanPacks already in scanning!");
Expand All @@ -55,18 +62,22 @@ public void rescanPacks() {
PackUtil.openPackFileSystem(packFile, path -> {
Path dynamicPackPath = path.resolve(CLIENT_FILE);
if (Files.exists(dynamicPackPath)) {
Out.println(" + Pack " + packFile.getName() + " supported by mod!");
Out.println("+ Pack " + packFile.getName() + " supported by mod!");
try {
processPack(packFile, PackUtil.readJson(dynamicPackPath));
} catch (IOException e) {
throw new RuntimeException(e);
}
} else {
Out.println(" - Pack " + packFile.getName() + " not supported by mod.");
Out.println("- Pack " + packFile.getName() + " not supported by mod.");
}
});
} catch (Exception e) {
Out.error("Error while processing pack: " + packFile, e);
if (e instanceof FailedOpenPackFileSystemException) {
Out.warn("Error while processing pack " + packFile.getName() + ": " + e.getMessage());
} else {
Out.error("Error while processing pack: " + packFile.getName(), e);
}
}
}
isPacksScanning = false;
Expand Down Expand Up @@ -99,7 +110,7 @@ public boolean isNameIsDynamic(String name) {
}

public Pack getDynamicPackByMinecraftName(String name) {
for (Pack pack : packs) {
for (Pack pack : getPacks()) {
if (("file/" + pack.getName()).equals(name)) {
return pack;
}
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package com.adamcalculator.dynamicpack;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class InputValidator {
private static final Pattern CONTENT_ID_PATTERN = Pattern.compile("^[a-z0-9_:-]{2,128}$");

public static boolean isContentIdValid(String input) {
if (input == null) {
return false;
}
Matcher matcher = CONTENT_ID_PATTERN.matcher(input);
return matcher.matches();
}

public static boolean isPackNameValid(String input) {
if (input == null) {
return false;
}

return input.trim().length() < 64 && !input.trim().isEmpty() && !input.contains("\n") && !input.contains("\r") && !input.contains("\b");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ public static boolean isHTTPTrafficAllowed() {

// DebugScreen allowed
public static boolean isDebugScreenAllowed() {
return true;
return false;
}

public static void debugNetwork() {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package com.adamcalculator.dynamicpack;

import com.adamcalculator.dynamicpack.util.FailedOpenPackFileSystemException;
import org.json.JSONObject;

import java.io.File;
Expand Down Expand Up @@ -56,7 +57,7 @@ public static void openPackFileSystem(File pack, Consumer<Path> consumer) throws
}

} else {
throw new RuntimeException("Failed to open pack file system");
throw new FailedOpenPackFileSystemException("Failed to open pack file system");
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,18 +1,19 @@
package com.adamcalculator.dynamicpack.pack;

import com.adamcalculator.dynamicpack.DynamicPackModBase;
import com.adamcalculator.dynamicpack.InputValidator;
import com.adamcalculator.dynamicpack.Mod;
import com.adamcalculator.dynamicpack.PackUtil;
import com.adamcalculator.dynamicpack.sync.PackSyncProgress;
import com.adamcalculator.dynamicpack.util.AFiles;
import com.adamcalculator.dynamicpack.util.FileDownloadConsumer;
import com.adamcalculator.dynamicpack.util.Out;
import com.adamcalculator.dynamicpack.util.Urls;
import org.json.JSONArray;
import org.json.JSONObject;

import java.io.IOException;
import java.nio.file.Path;
import java.rmi.RemoteException;
import java.security.NoSuchAlgorithmException;
import java.util.HashMap;
import java.util.function.LongConsumer;
Expand All @@ -24,7 +25,7 @@ public class DynamicRepoRemote extends Remote {


private Pack parent;

private JSONObject cachedCurrentJson;
protected String url;
protected String buildUrl;
protected String packUrl;
Expand All @@ -37,8 +38,9 @@ public class DynamicRepoRemote extends Remote {
public DynamicRepoRemote() {
}

public void init(Pack pack, JSONObject remote) {
public void init(Pack pack, JSONObject remote, JSONObject current) {
this.parent = pack;
this.cachedCurrentJson = current;
this.url = remote.getString("url");
this.buildUrl = url + "/" + REPO_BUILD;
this.packUrl = url + "/" + REPO_JSON;
Expand All @@ -62,12 +64,50 @@ public void init(Pack pack, JSONObject remote) {
@Override
public boolean checkUpdateAvailable() throws IOException {
String content = Urls.parseContent(buildUrl, 64).trim();
return parent.getCurrentBuild() != Long.parseLong(content);
return getCurrentBuild() != Long.parseLong(content);
}

public long getCurrentBuild() {
return cachedCurrentJson.optLong("build", -1);
}


// currently not using. but in feature this may be used in settings screen to Enable/disable contents
public void updateCurrentKnownContents(JSONArray repoContents) {
if (cachedCurrentJson.has("known_contents")) {
cachedCurrentJson.remove("known_contents");
}
JSONObject newKnown = new JSONObject();
cachedCurrentJson.put("known_contents", newKnown);
for (Object _repoContent : repoContents) {
JSONObject repoContent = (JSONObject) _repoContent;
String id = repoContent.getString("id");
boolean required = repoContent.optBoolean("required", false);
JSONObject jsonObject = new JSONObject()
.put("hash", repoContent.getString("hash"));
if (required) {
jsonObject.put("required", true);
}
newKnown.put(id, jsonObject);
}
}

public String getCurrentPackContentHash(String id) {
if (cachedCurrentJson.has("known_contents")) {
try {
return cachedCurrentJson.getJSONObject("known_contents").getJSONObject(id).getString("hash");

} catch (Exception e) {
// if hash not found
return null;
}
}
return null;
}


@Override
public boolean sync(PackSyncProgress progress) throws IOException, NoSuchAlgorithmException {
public boolean sync(PackSyncProgress progress, boolean manually) throws IOException, NoSuchAlgorithmException {
PackUtil.openPackFileSystem(parent.getLocation(), path -> {
try {
sync0(progress, path);
Expand Down Expand Up @@ -105,11 +145,8 @@ public void onUpdate(FileDownloadConsumer it) {
}

String remoteName = repoJson.getString("name");
if (remoteName.isBlank()) {
throw new RuntimeException("Name of remote pack can't be blank");
}
if (remoteName.trim().length() > 50) {
throw new RuntimeException("Length of name pack can't > 50");
if (!InputValidator.isPackNameValid(remoteName)) {
throw new RuntimeException("Remote name of pack not valid.");
}


Expand All @@ -123,6 +160,7 @@ public void onUpdate(FileDownloadConsumer it) {
throw e;
}
parent.getPackJson().getJSONObject("current").put("build", repoJson.getLong("build"));
parent.updateJsonLatestUpdate();

AFiles.nioWriteText(path.resolve(DynamicPackModBase.CLIENT_FILE), parent.getPackJson().toString(2));
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,26 +1,20 @@
package com.adamcalculator.dynamicpack.pack;

import com.adamcalculator.dynamicpack.DynamicPackModBase;
import com.adamcalculator.dynamicpack.IDValidator;
import com.adamcalculator.dynamicpack.InputValidator;
import com.adamcalculator.dynamicpack.Mod;
import com.adamcalculator.dynamicpack.PackUtil;
import com.adamcalculator.dynamicpack.sync.PackSyncProgress;
import com.adamcalculator.dynamicpack.sync.state.StateFileDeleted;
import com.adamcalculator.dynamicpack.util.AFiles;
import com.adamcalculator.dynamicpack.util.FileDownloadConsumer;
import com.adamcalculator.dynamicpack.util.Hashes;
import com.adamcalculator.dynamicpack.util.Urls;
import com.adamcalculator.dynamicpack.util.*;
import org.json.JSONArray;
import org.json.JSONObject;

import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.*;

public class DynamicRepoSyncProcessV1 {
private final DynamicRepoRemote remote;
Expand Down Expand Up @@ -54,18 +48,31 @@ public void run() throws IOException {
progress.textLog("File deleted from resource-pack: " + s);
AFiles.nioSmartDelete(path);
}

try {
remote.updateCurrentKnownContents(repoJson.getJSONArray("contents"));
} catch (Exception e) {
Out.error("Error while update known_packs. Not fatal", e);
}
}

public void close() throws IOException {
}

private void processContent(JSONObject jsonContent) throws IOException {
String id = jsonContent.getString("id");
if (!IDValidator.isValid(id)) {
if (!InputValidator.isContentIdValid(id)) {
throw new RuntimeException("Id of content is not valid.");
}

String contentRemoteHash = jsonContent.getString("hash");
String localCache = remote.getCurrentPackContentHash(id);
if (Objects.equals(localCache, contentRemoteHash)) {
progress.textLog("Content '" + id + "' local hash is equal with remote...");
} else {
progress.textLog("Content '" + id + "' local hash different with remote or null.");
}

String url = jsonContent.getString("url");
String urlCompressed = jsonContent.optString("url_compressed", null);
boolean compressSupported = urlCompressed != null;
Expand Down Expand Up @@ -180,12 +187,16 @@ private List<JSONObject> calcActiveContents() {
while (i < contents.length()) {
JSONObject content = contents.getJSONObject(i);
String id = content.getString("id");

if (!InputValidator.isContentIdValid(id)) {
throw new RuntimeException("Id of content is not valid.");
}

if (remote.isContentActive(id) || content.optBoolean("required", false)) {
activeContents.add(content);
}
i++;
}

return activeContents;
}
}
Loading
Loading