Skip to content

Commit 2641871

Browse files
committed
Add PHP implementation for Jummania URL encryption/decryption
This commit introduces a PHP script that replicates the functionality of the Java Jummania class. It handles AES-128 encryption/decryption with obfuscated keys and provides a corresponding Java code snippet for interoperability. Additionally, the `.idea/php.xml` file was updated to specify the PHP language level.
1 parent 4cb003d commit 2641871

File tree

2 files changed

+131
-0
lines changed

2 files changed

+131
-0
lines changed

.idea/php.xml

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

index.php

Lines changed: 130 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,130 @@
1+
<?php
2+
/**
3+
* Jummania.php
4+
*
5+
* Replicates the Java Jummania class in PHP:
6+
* 1. Generates an AES-128 key, encodes it without padding, shifts each char +1
7+
* 2. Reverses that to recover the raw key
8+
* 3. Encrypts a URL with AES/ECB/PKCS5Padding, Base64-encodes it, then shifts each char −1
9+
* 4. Shifts back +1, Base64-decodes, and decrypts to recover the original URL
10+
*/
11+
12+
13+
$string = $_GET['string'] ?? null;
14+
15+
if (!$string) {
16+
// Build current URL without query string
17+
$scheme = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off') ? "https" : "http";
18+
$host = $_SERVER['HTTP_HOST'];
19+
$path = $_SERVER['PHP_SELF']; // script path
20+
21+
$currentUrl = $scheme . "://" . $host . $path;
22+
23+
$javaCode = <<<JAVA
24+
Exception in thread "main" java.lang.IllegalStateException: string must not be null
25+
at com.jummania.link.Main.main(Main.java:10)
26+
27+
Usage: {$currentUrl}?string=your_encrypted_text_here
28+
JAVA;
29+
30+
showJavaCode($javaCode);
31+
exit();
32+
}
33+
34+
35+
// 1. Generate a lightweight AES-128 key (16 raw bytes)
36+
$base64Key = rtrim(base64_encode(random_bytes(16)), '=');
37+
38+
// 2. Obfuscate the key: shift each character by +1
39+
$encKeyChars = '';
40+
for ($i = 0, $l = strlen($base64Key); $i < $l; $i++) {
41+
$encKeyChars .= chr(ord($base64Key[$i]) + 1);
42+
}
43+
44+
// 3. Function to reverse key obfuscation
45+
function getSecretKey(string $keyStr): string
46+
{
47+
$decoded = '';
48+
for ($i = 0, $l = strlen($keyStr); $i < $l; $i++) {
49+
$decoded .= chr(ord($keyStr[$i]) - 1);
50+
}
51+
return base64_decode($decoded);
52+
}
53+
54+
$secretKey = getSecretKey($encKeyChars);
55+
56+
// 4. Encrypt the text and shift each char by -1
57+
function encryptShift(string $plainText, string $key): string
58+
{
59+
$encrypted = openssl_encrypt($plainText, 'AES-128-ECB', $key, OPENSSL_RAW_DATA);
60+
$b64 = base64_encode($encrypted);
61+
62+
$shifted = '';
63+
for ($i = 0, $l = strlen($b64); $i < $l; $i++) {
64+
$shifted .= chr(ord($b64[$i]) - 1);
65+
}
66+
return $shifted;
67+
}
68+
69+
$shiftedEnc = encryptShift($string, $secretKey);
70+
71+
72+
$javaCode = <<<JAVA
73+
public class Jummania {
74+
public static String getString() {
75+
javax.crypto.SecretKey secretKey = getSecretKey("$encKeyChars");
76+
return getString(secretKey, "$shiftedEnc");
77+
}
78+
79+
public static javax.crypto.SecretKey getSecretKey(String key) {
80+
String string = shiftChars(key, -1);
81+
byte[] decodedKey = java.util.Base64.getDecoder().decode(string);
82+
return new javax.crypto.spec.SecretKeySpec(decodedKey, 0, decodedKey.length, "AES");
83+
}
84+
85+
public static String getString(javax.crypto.SecretKey secretKey, String encryptedText) {
86+
try {
87+
String string = shiftChars(encryptedText, 1);
88+
java.util.Base64.Decoder decoder = java.util.Base64.getDecoder();
89+
byte[] encryptedTextByte = decoder.decode(string);
90+
javax.crypto.Cipher cipher = javax.crypto.Cipher.getInstance("AES");
91+
cipher.init(javax.crypto.Cipher.DECRYPT_MODE, secretKey);
92+
return new String(cipher.doFinal(encryptedTextByte));
93+
} catch (Exception e) {
94+
return null;
95+
}
96+
97+
}
98+
99+
public static String shiftChars(String input, int shift) {
100+
StringBuilder result = new StringBuilder();
101+
for (char c : input.toCharArray()) {
102+
result.append((char) (c + shift));
103+
}
104+
return result.toString();
105+
}
106+
}
107+
JAVA;
108+
109+
showJavaCode($javaCode);
110+
111+
function showJavaCode(string $javaCode)
112+
{
113+
?>
114+
<!DOCTYPE html>
115+
<html lang="en">
116+
<head>
117+
<meta charset="UTF-8">
118+
<title>Java Code</title>
119+
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/styles/default.min.css">
120+
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/highlight.min.js"></script>
121+
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/java.min.js"></script>
122+
<script>hljs.highlightAll();</script>
123+
</head>
124+
<body>
125+
<pre><code class="language-java"><?php echo htmlspecialchars($javaCode); ?></code></pre>
126+
</body>
127+
</html>
128+
<?php
129+
exit();
130+
}

0 commit comments

Comments
 (0)