Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
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
32 changes: 28 additions & 4 deletions src/main/java/com/rarchives/ripme/ripper/rippers/Rule34Ripper.java
Original file line number Diff line number Diff line change
Expand Up @@ -10,20 +10,41 @@
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;

import com.rarchives.ripme.ripper.AbstractHTMLRipper;
import com.rarchives.ripme.ui.RipStatusMessage.STATUS;
import com.rarchives.ripme.utils.Http;
import com.rarchives.ripme.utils.Utils;

public class Rule34Ripper extends AbstractHTMLRipper {

private static final Logger logger = LogManager.getLogger(Rule34Ripper.class);

public Rule34Ripper(URL url) throws IOException {
super(url);
}

private String apiUrl;
private int pageNumber = 0;
private String apiKey;
private String userId;

private void loadConfig() {
apiKey = Utils.getConfigString("rule34.api_key", "");
userId = Utils.getConfigString("rule34.user_id", "");
if (apiKey.isEmpty() || userId.isEmpty()) {
sendUpdate(STATUS.DOWNLOAD_WARN,
"rule34.xxx requires API credentials. Set rule34.api_key and rule34.user_id in config. "
+ "Get them from https://rule34.xxx/index.php?page=account&s=options");
logger.warn("Missing rule34 API credentials. Requests may fail with 403.");
} else {
logger.info("Using rule34 API credentials for user_id: " + userId);
}
}

@Override
public String getHost() {
Expand Down Expand Up @@ -54,15 +75,18 @@ public String getGID(URL url) throws MalformedURLException {
}

public URL getAPIUrl() throws MalformedURLException, URISyntaxException {
URL urlToReturn = new URI("https://rule34.xxx/index.php?page=dapi&s=post&q=index&limit=100&tags=" + getGID(url)).toURL();
return urlToReturn;
String baseUrl = "https://rule34.xxx/index.php?page=dapi&s=post&q=index&limit=100&tags=" + getGID(url);
Comment thread
apoorvdarshan marked this conversation as resolved.
Outdated
if (apiKey != null && !apiKey.isEmpty() && userId != null && !userId.isEmpty()) {
Comment thread
apoorvdarshan marked this conversation as resolved.
Outdated
baseUrl += "&api_key=" + apiKey + "&user_id=" + userId;
}
return new URI(baseUrl).toURL();
}

@Override
public Document getFirstPage() throws IOException, URISyntaxException {
loadConfig();
apiUrl = getAPIUrl().toExternalForm();
// "url" is an instance field of the superclass
return Http.url(getAPIUrl()).get();
return Http.url(apiUrl).get();
}

@Override
Expand Down
4 changes: 4 additions & 0 deletions src/main/resources/rip.properties
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,10 @@ twitter.auth = VW9Ybjdjb1pkd2J0U3kwTUh2VXVnOm9GTzVQVzNqM29LQU1xVGhnS3pFZzhKbGVqb
tumblr.auth = JFNLu3CbINQjRdUvZibXW9VpSEVYYtiPJ86o8YmvgLZIoKyuNX
gw.api = gonewild

# Rule34 API credentials - get from https://rule34.xxx/index.php?page=account&s=options
# rule34.api_key =
# rule34.user_id =

twitter.max_requests = 10
twitter.rip_retweets = false
twitter.exclude_replies = true
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,12 @@
import org.junit.jupiter.api.Test;

import com.rarchives.ripme.ripper.rippers.Rule34Ripper;
import com.rarchives.ripme.utils.Utils;

public class Rule34RipperTest extends RippersTest {
@Test
@Tag("flaky")
public void testShesFreakyRip() throws IOException, URISyntaxException {
public void testRule34Rip() throws IOException, URISyntaxException {
Rule34Ripper ripper = new Rule34Ripper(
new URI("https://rule34.xxx/index.php?page=post&s=list&tags=bimbo").toURL());
testRipper(ripper);
Expand All @@ -27,4 +28,54 @@ public void testGetGID() throws IOException, URISyntaxException {
Assertions.assertEquals("bimbo", ripper.getGID(url));
}

@Test
public void testGetAPIUrlWithCredentials() throws IOException, URISyntaxException {
Utils.setConfigString("rule34.api_key", "testapikey123");
Utils.setConfigString("rule34.user_id", "12345");
try {
URL url = new URI("https://rule34.xxx/index.php?page=post&s=list&tags=bimbo").toURL();
Rule34Ripper ripper = new Rule34Ripper(url);

// Trigger loadConfig() via getFirstPage(); HTTP call will fail in test env
try {
ripper.getFirstPage();
} catch (IOException e) {
// Expected in test environment
}

String apiUrlString = ripper.getAPIUrl().toExternalForm();
Assertions.assertTrue(apiUrlString.contains("api_key=testapikey123"),
"API URL should contain api_key parameter");
Assertions.assertTrue(apiUrlString.contains("user_id=12345"),
"API URL should contain user_id parameter");
} finally {
Utils.setConfigString("rule34.api_key", "");
Utils.setConfigString("rule34.user_id", "");
}
}

@Test
public void testGetAPIUrlWithoutCredentials() throws IOException, URISyntaxException {
Utils.setConfigString("rule34.api_key", "");
Utils.setConfigString("rule34.user_id", "");
try {
URL url = new URI("https://rule34.xxx/index.php?page=post&s=list&tags=bimbo").toURL();
Rule34Ripper ripper = new Rule34Ripper(url);

try {
ripper.getFirstPage();
} catch (IOException e) {
// Expected in test environment
}

String apiUrlString = ripper.getAPIUrl().toExternalForm();
Assertions.assertFalse(apiUrlString.contains("api_key="),
"API URL should not contain api_key when unconfigured");
Assertions.assertFalse(apiUrlString.contains("user_id="),
"API URL should not contain user_id when unconfigured");
} finally {
Utils.setConfigString("rule34.api_key", "");
Utils.setConfigString("rule34.user_id", "");
}
}
}