From 8d04c5c719c2392880a653926758fe309e9b4333 Mon Sep 17 00:00:00 2001 From: Rob Hanlon <69870+robhanlon22@users.noreply.github.com> Date: Wed, 29 Nov 2023 16:29:51 -0800 Subject: [PATCH 1/2] Introduce code formatting + git hooks Adds the spotless gradle plugin for a formatting abstraction; prettier for formatting Java, Java properties, YAML, and Markdown; and pre-commit to tie the aforementioned into a pre-commit hook. --- .github/workflows/test.yml | 32 +- .greclipse.properties | 4 + .pre-commit-config.yaml | 14 + .prettierrc.yaml | 4 + CHANGELOG.md | 5 +- README.md | 34 +- build.gradle | 55 +- src/main/java/org/sqids/Sqids.java | 1215 ++++++++++--------- src/test/java/org/sqids/AlphabetTests.java | 36 +- src/test/java/org/sqids/BlockListTests.java | 77 +- src/test/java/org/sqids/EncodeTests.java | 142 ++- src/test/java/org/sqids/MinLengthTests.java | 123 +- 12 files changed, 997 insertions(+), 744 deletions(-) create mode 100644 .greclipse.properties create mode 100644 .pre-commit-config.yaml create mode 100644 .prettierrc.yaml diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 51aea9e..3b3aa82 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -1,23 +1,23 @@ name: Continuous Testing on: - push: - branches: [ "main" ] - pull_request: - branches: [ "main" ] + push: + branches: ["main"] + pull_request: + branches: ["main"] permissions: - contents: read + contents: read jobs: - test: - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v4 - - uses: actions/setup-java@v3 - with: - java-version: '8' - distribution: 'temurin' - - uses: gradle/gradle-build-action@v2 - - run: gradle wrapper - - run: ./gradlew test + test: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-java@v3 + with: + java-version: "11" + distribution: "temurin" + - uses: gradle/gradle-build-action@v2 + - run: gradle wrapper + - run: ./gradlew check diff --git a/.greclipse.properties b/.greclipse.properties new file mode 100644 index 0000000..812ab1b --- /dev/null +++ b/.greclipse.properties @@ -0,0 +1,4 @@ +groovy.formatter.remove.unnecessary.semicolons = true +org.eclipse.jdt.core.formatter.indent_empty_lines = false +org.eclipse.jdt.core.formatter.tabulation.char = space +org.eclipse.jdt.core.formatter.tabulation.size = 4 diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml new file mode 100644 index 0000000..8500e9d --- /dev/null +++ b/.pre-commit-config.yaml @@ -0,0 +1,14 @@ +repos: + - repo: local + hooks: + - id: spotless + name: spotless + language: system + entry: ./gradlew spotlessApply + pass_filenames: false + always_run: true + - id: git-diff + name: git-diff + language: system + entry: git --no-pager diff --color --exit-code + always_run: true diff --git a/.prettierrc.yaml b/.prettierrc.yaml new file mode 100644 index 0000000..5a2c2e6 --- /dev/null +++ b/.prettierrc.yaml @@ -0,0 +1,4 @@ +plugins: + - prettier-plugin-java + - prettier-plugin-properties +tabWidth: 4 diff --git a/CHANGELOG.md b/CHANGELOG.md index d3e7bb3..867c602 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,6 @@ # CHANGELOG **v0.1.0:** -- Initial implementation of [the spec](https://github.com/sqids/sqids-spec) -- Packaging & cleanup \ No newline at end of file + +- Initial implementation of [the spec](https://github.com/sqids/sqids-spec) +- Packaging & cleanup diff --git a/README.md b/README.md index a04ce77..2fc486c 100644 --- a/README.md +++ b/README.md @@ -1,36 +1,35 @@ # [Sqids Java](https://sqids.org/java) -[Sqids](https://sqids.org/java) (*pronounced "squids"*) is a small library that lets you **generate unique IDs from +[Sqids](https://sqids.org/java) (_pronounced "squids"_) is a small library that lets you **generate unique IDs from numbers**. It's good for link shortening, fast & URL-safe ID generation and decoding back into numbers for quicker database lookups. Features: -- **Encode multiple numbers** - generate short IDs from one or several non-negative numbers -- **Quick decoding** - easily decode IDs back into numbers -- **Unique IDs** - generate unique IDs by shuffling the alphabet once -- **ID padding** - provide minimum length to make IDs more uniform -- **URL safe** - auto-generated IDs do not contain common profanity -- **Randomized output** - Sequential input provides nonconsecutive IDs -- **Many implementations** - Support for [40+ programming languages](https://sqids.org/) +- **Encode multiple numbers** - generate short IDs from one or several non-negative numbers +- **Quick decoding** - easily decode IDs back into numbers +- **Unique IDs** - generate unique IDs by shuffling the alphabet once +- **ID padding** - provide minimum length to make IDs more uniform +- **URL safe** - auto-generated IDs do not contain common profanity +- **Randomized output** - Sequential input provides nonconsecutive IDs +- **Many implementations** - Support for [40+ programming languages](https://sqids.org/) ## 🧰 Use-cases Good for: -- Generating IDs for public URLs (eg: link shortening) -- Generating IDs for internal systems (eg: event tracking) -- Decoding for quicker database lookups (eg: by primary keys) +- Generating IDs for public URLs (eg: link shortening) +- Generating IDs for internal systems (eg: event tracking) +- Decoding for quicker database lookups (eg: by primary keys) Not good for: -- Sensitive data (this is not an encryption library) -- User IDs (can be decoded revealing user count) - +- Sensitive data (this is not an encryption library) +- User IDs (can be decoded revealing user count) ## System Requirements -Java 8 or higher is required. +Java 8 or higher is required. ## 🚀 Getting started @@ -38,6 +37,7 @@ Download and Import Sqids via: ```java import org.sqids.Sqids; + ``` ## 👩‍💻 Examples @@ -55,7 +55,7 @@ List numbers=sqids.decode(id); // [1, 2, 3] > important to your design that IDs are canonical, you have to manually re-encode decoded numbers and check that the > generated ID matches. -Enforce a *minimum* length for IDs: +Enforce a _minimum_ length for IDs: ```java Sqids sqids=Sqids.builder() @@ -87,4 +87,4 @@ List numbers=sqids.decode(id); // [1, 2, 3] ## 📝 License -[MIT](LICENSE) \ No newline at end of file +[MIT](LICENSE) diff --git a/build.gradle b/build.gradle index 8dfa99f..8e633fc 100644 --- a/build.gradle +++ b/build.gradle @@ -1,4 +1,6 @@ plugins { + id 'com.diffplug.spotless' version '6.23.1' + id 'com.github.node-gradle.node' version '7.0.1' id 'java-library' id 'maven-publish' id 'signing' @@ -7,7 +9,7 @@ plugins { group = 'org.sqids' version = '0.1.0-SNAPSHOT' -String rootArtifactiId = 'sqids' +String rootArtifactId = 'sqids' String projectUrl = 'https://sqids.org/java' repositories { @@ -17,7 +19,7 @@ repositories { dependencies { testImplementation platform('org.junit:junit-bom:5.10.0') testImplementation 'org.junit.jupiter:junit-jupiter' - testRuntimeOnly("org.junit.platform:junit-platform-launcher") + testRuntimeOnly 'org.junit.platform:junit-platform-launcher' } test { @@ -34,10 +36,9 @@ java { publishing { publications { - mavenJava(MavenPublication) { groupId = group - artifactId = rootArtifactiId + artifactId = rootArtifactId version = version from components.java pom { @@ -45,9 +46,9 @@ publishing { description = 'Generate short YouTube-looking IDs from numbers.' url = projectUrl properties = [ - "parent.groupId": "org.sonatype.oss", - "parent.artifactId": "oss-parent", - "parent.version": "7" + 'parent.groupId': 'org.sonatype.oss', + 'parent.artifactId': 'oss-parent', + 'parent.version': '7' ] licenses { license { @@ -72,12 +73,12 @@ publishing { } repositories { maven { - def releasesRepoUrl = 'https://s01.oss.sonatype.org/service/local/staging/deploy/maven2/' - def snapshotsRepoUrl = 'https://s01.oss.sonatype.org/content/repositories/snapshots/' + String releasesRepoUrl = 'https://s01.oss.sonatype.org/service/local/staging/deploy/maven2/' + String snapshotsRepoUrl = 'https://s01.oss.sonatype.org/content/repositories/snapshots/' url = version.endsWith('SNAPSHOT') ? snapshotsRepoUrl : releasesRepoUrl credentials { - username "${System.getenv("SONATYPE_USERNAME")}" - password "${System.getenv("SONATYPE_PASSWORD")}" + username System.getenv('SONATYPE_USERNAME') + password System.getenv('SONATYPE_PASSWORD') } } } @@ -86,3 +87,35 @@ publishing { sign publishing.publications.mavenJava } } + +node { + download = true +} + +String nodeSetup = 'nodeSetup' +String npmSetup = 'npmSetup' + +spotless { + format 'prettier', { + target '**/*.java', '**/*.properties', '**/*.md', '**/*.yml', '**/*.yaml' + targetExclude 'bin/**/*', 'gradle/**/*' + + boolean isWindows = System.getProperty('os.name').toLowerCase().contains('windows') + String nodeExec = isWindows ? '/node.exe' : '/bin/node' + String npmExec = isWindows ? '/npm.cmd' : '/bin/npm' + + prettier(['prettier': '3.1.0', 'prettier-plugin-java': '2.2.0', 'prettier-plugin-properties': '0.3.0']) + .npmInstallCache() + .npmExecutable("${tasks.named(npmSetup).get().npmDir.get()}${npmExec}") + .nodeExecutable("${tasks.named(nodeSetup).get().nodeDir.get()}${nodeExec}") + .configFile('.prettierrc.yaml') + } + + groovyGradle { + greclipse().configFile('.greclipse.properties') + } +} + +tasks.named('spotlessPrettier').configure { task -> + task.dependsOn(nodeSetup, npmSetup) +} diff --git a/src/main/java/org/sqids/Sqids.java b/src/main/java/org/sqids/Sqids.java index 58ff384..bb87a93 100644 --- a/src/main/java/org/sqids/Sqids.java +++ b/src/main/java/org/sqids/Sqids.java @@ -17,10 +17,11 @@ * This implementation is immutable and thread-safe, no lock is necessary. */ public class Sqids { + /** - * The minimum allowable length of the alphabet used for encoding and - * decoding Sqids. - */ + * The minimum allowable length of the alphabet used for encoding and + * decoding Sqids. + */ public static final int MIN_ALPHABET_LENGTH = 3; /** @@ -46,23 +47,36 @@ private Sqids(final Builder builder) { final Set blockList = new HashSet<>(builder.blockList); if (alphabet.getBytes().length != alphabetLength) { - throw new IllegalArgumentException("Alphabet cannot contain multibyte characters"); + throw new IllegalArgumentException( + "Alphabet cannot contain multibyte characters" + ); } if (alphabetLength < MIN_ALPHABET_LENGTH) { - throw new IllegalArgumentException("Alphabet length must be at least " + MIN_ALPHABET_LENGTH); + throw new IllegalArgumentException( + "Alphabet length must be at least " + MIN_ALPHABET_LENGTH + ); } - if (new HashSet<>(Arrays.asList(alphabet.split(""))).size() != alphabetLength) { - throw new IllegalArgumentException("Alphabet must contain unique characters"); + if ( + new HashSet<>(Arrays.asList(alphabet.split(""))).size() != + alphabetLength + ) { + throw new IllegalArgumentException( + "Alphabet must contain unique characters" + ); } if (minLength < 0 || minLength > MIN_LENGTH_LIMIT) { - throw new IllegalArgumentException("Minimum length has to be between 0 and " + MIN_LENGTH_LIMIT); + throw new IllegalArgumentException( + "Minimum length has to be between 0 and " + MIN_LENGTH_LIMIT + ); } final Set filteredBlockList = new HashSet<>(); - final List alphabetChars = new ArrayList<>(Arrays.asList(alphabet.toLowerCase().split(""))); + final List alphabetChars = new ArrayList<>( + Arrays.asList(alphabet.toLowerCase().split("")) + ); for (String word : blockList) { if (word.length() >= MIN_BLOCK_LIST_WORD_LENGTH) { word = word.toLowerCase(); @@ -102,7 +116,9 @@ public String encode(final List numbers) { } for (Long num : numbers) { if (num < 0) { - throw new RuntimeException("Encoding supports numbers between 0 and " + Long.MAX_VALUE); + throw new RuntimeException( + "Encoding supports numbers between 0 and " + Long.MAX_VALUE + ); } } return encodeNumbers(numbers); @@ -134,9 +150,9 @@ public List decode(final String id) { final char prefix = id.charAt(0); final int offset = this.alphabet.indexOf(prefix); String alphabet = new StringBuilder(this.alphabet.substring(offset)) - .append(this.alphabet, 0, offset) - .reverse() - .toString(); + .append(this.alphabet, 0, offset) + .reverse() + .toString(); int index = 1; while (true) { @@ -162,21 +178,33 @@ private String encodeNumbers(final List numbers) { return this.encodeNumbers(numbers, 0); } - private String encodeNumbers(final List numbers, final int increment) { + private String encodeNumbers( + final List numbers, + final int increment + ) { if (increment > this.alphabetLength) { - throw new RuntimeException("Reached max attempts to re-generate the ID"); + throw new RuntimeException( + "Reached max attempts to re-generate the ID" + ); } final int numberSize = numbers.size(); long offset = numberSize; for (int i = 0; i < numberSize; i++) { - offset = offset + this.alphabet.charAt((int) (numbers.get(i) % this.alphabetLength)) + i; + offset = + offset + + this.alphabet.charAt( + (int) (numbers.get(i) % this.alphabetLength) + ) + + i; } offset %= this.alphabetLength; offset = (offset + increment) % this.alphabetLength; - final StringBuilder alphabetB = new StringBuilder(this.alphabet.substring((int) offset)) - .append(this.alphabet, 0, (int) offset); + final StringBuilder alphabetB = new StringBuilder( + this.alphabet.substring((int) offset) + ) + .append(this.alphabet, 0, (int) offset); final char prefix = alphabetB.charAt(0); String alphabet = alphabetB.reverse().toString(); final StringBuilder id = new StringBuilder().append(prefix); @@ -193,7 +221,11 @@ private String encodeNumbers(final List numbers, final int increment) { id.append(alphabet.charAt(0)); while (this.minLength - id.length() > 0) { alphabet = shuffle(alphabet); - id.append(alphabet, 0, Math.min(this.minLength - id.length(), alphabet.length())); + id.append( + alphabet, + 0, + Math.min(this.minLength - id.length(), alphabet.length()) + ); } } @@ -231,7 +263,12 @@ private StringBuilder toId(long num, final String alphabet) { return id.reverse(); } - private long toNumber(final String id, final int fromInclusive, final int toExclusive, final String alphabet) { + private long toNumber( + final String id, + final int fromInclusive, + final int toExclusive, + final String alphabet + ) { int alphabetLength = alphabet.length(); long number = 0; for (int i = fromInclusive; i < toExclusive; i++) { @@ -251,7 +288,10 @@ private boolean isBlockedId(final String id) { return true; } } else if (Character.isDigit(word.charAt(0))) { - if (lowercaseId.startsWith(word) || lowercaseId.endsWith(word)) { + if ( + lowercaseId.startsWith(word) || + lowercaseId.endsWith(word) + ) { return true; } } else if (lowercaseId.contains(word)) { @@ -266,10 +306,12 @@ private boolean isBlockedId(final String id) { * Default Sqids' {@code Builder}. */ public static final class Builder { + /** * Default Alphabet used by {@code Builder}. */ - public static final String DEFAULT_ALPHABET = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; + public static final String DEFAULT_ALPHABET = + "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; /** * Default Minimum length used by {@code Builder}. @@ -281,566 +323,572 @@ public static final class Builder { * * Note: This is a Immutable Set. */ - public static final Set DEFAULT_BLOCK_LIST = Collections.unmodifiableSet(Stream.of( - "1d10t", - "1d1ot", - "1di0t", - "1diot", - "1eccacu10", - "1eccacu1o", - "1eccacul0", - "1eccaculo", - "1mbec11e", - "1mbec1le", - "1mbeci1e", - "1mbecile", - "a11upat0", - "a11upato", - "a1lupat0", - "a1lupato", - "aand", - "ah01e", - "ah0le", - "aho1e", - "ahole", - "al1upat0", - "al1upato", - "allupat0", - "allupato", - "ana1", - "ana1e", - "anal", - "anale", - "anus", - "arrapat0", - "arrapato", - "arsch", - "arse", - "ass", - "b00b", - "b00be", - "b01ata", - "b0ceta", - "b0iata", - "b0ob", - "b0obe", - "b0sta", - "b1tch", - "b1te", - "b1tte", - "ba1atkar", - "balatkar", - "bastard0", - "bastardo", - "batt0na", - "battona", - "bitch", - "bite", - "bitte", - "bo0b", - "bo0be", - "bo1ata", - "boceta", - "boiata", - "boob", - "boobe", - "bosta", - "bran1age", - "bran1er", - "bran1ette", - "bran1eur", - "bran1euse", - "branlage", - "branler", - "branlette", - "branleur", - "branleuse", - "c0ck", - "c0g110ne", - "c0g11one", - "c0g1i0ne", - "c0g1ione", - "c0gl10ne", - "c0gl1one", - "c0gli0ne", - "c0glione", - "c0na", - "c0nnard", - "c0nnasse", - "c0nne", - "c0u111es", - "c0u11les", - "c0u1l1es", - "c0u1lles", - "c0ui11es", - "c0ui1les", - "c0uil1es", - "c0uilles", - "c11t", - "c11t0", - "c11to", - "c1it", - "c1it0", - "c1ito", - "cabr0n", - "cabra0", - "cabrao", - "cabron", - "caca", - "cacca", - "cacete", - "cagante", - "cagar", - "cagare", - "cagna", - "cara1h0", - "cara1ho", - "caracu10", - "caracu1o", - "caracul0", - "caraculo", - "caralh0", - "caralho", - "cazz0", - "cazz1mma", - "cazzata", - "cazzimma", - "cazzo", - "ch00t1a", - "ch00t1ya", - "ch00tia", - "ch00tiya", - "ch0d", - "ch0ot1a", - "ch0ot1ya", - "ch0otia", - "ch0otiya", - "ch1asse", - "ch1avata", - "ch1er", - "ch1ng0", - "ch1ngadaz0s", - "ch1ngadazos", - "ch1ngader1ta", - "ch1ngaderita", - "ch1ngar", - "ch1ngo", - "ch1ngues", - "ch1nk", - "chatte", - "chiasse", - "chiavata", - "chier", - "ching0", - "chingadaz0s", - "chingadazos", - "chingader1ta", - "chingaderita", - "chingar", - "chingo", - "chingues", - "chink", - "cho0t1a", - "cho0t1ya", - "cho0tia", - "cho0tiya", - "chod", - "choot1a", - "choot1ya", - "chootia", - "chootiya", - "cl1t", - "cl1t0", - "cl1to", - "clit", - "clit0", - "clito", - "cock", - "cog110ne", - "cog11one", - "cog1i0ne", - "cog1ione", - "cogl10ne", - "cogl1one", - "cogli0ne", - "coglione", - "cona", - "connard", - "connasse", - "conne", - "cou111es", - "cou11les", - "cou1l1es", - "cou1lles", - "coui11es", - "coui1les", - "couil1es", - "couilles", - "cracker", - "crap", - "cu10", - "cu1att0ne", - "cu1attone", - "cu1er0", - "cu1ero", - "cu1o", - "cul0", - "culatt0ne", - "culattone", - "culer0", - "culero", - "culo", - "cum", - "cunt", - "d11d0", - "d11do", - "d1ck", - "d1ld0", - "d1ldo", - "damn", - "de1ch", - "deich", - "depp", - "di1d0", - "di1do", - "dick", - "dild0", - "dildo", - "dyke", - "encu1e", - "encule", - "enema", - "enf01re", - "enf0ire", - "enfo1re", - "enfoire", - "estup1d0", - "estup1do", - "estupid0", - "estupido", - "etr0n", - "etron", - "f0da", - "f0der", - "f0ttere", - "f0tters1", - "f0ttersi", - "f0tze", - "f0utre", - "f1ca", - "f1cker", - "f1ga", - "fag", - "fica", - "ficker", - "figa", - "foda", - "foder", - "fottere", - "fotters1", - "fottersi", - "fotze", - "foutre", - "fr0c10", - "fr0c1o", - "fr0ci0", - "fr0cio", - "fr0sc10", - "fr0sc1o", - "fr0sci0", - "fr0scio", - "froc10", - "froc1o", - "froci0", - "frocio", - "frosc10", - "frosc1o", - "frosci0", - "froscio", - "fuck", - "g00", - "g0o", - "g0u1ne", - "g0uine", - "gandu", - "go0", - "goo", - "gou1ne", - "gouine", - "gr0gnasse", - "grognasse", - "haram1", - "harami", - "haramzade", - "hund1n", - "hundin", - "id10t", - "id1ot", - "idi0t", - "idiot", - "imbec11e", - "imbec1le", - "imbeci1e", - "imbecile", - "j1zz", - "jerk", - "jizz", - "k1ke", - "kam1ne", - "kamine", - "kike", - "leccacu10", - "leccacu1o", - "leccacul0", - "leccaculo", - "m1erda", - "m1gn0tta", - "m1gnotta", - "m1nch1a", - "m1nchia", - "m1st", - "mam0n", - "mamahuev0", - "mamahuevo", - "mamon", - "masturbat10n", - "masturbat1on", - "masturbate", - "masturbati0n", - "masturbation", - "merd0s0", - "merd0so", - "merda", - "merde", - "merdos0", - "merdoso", - "mierda", - "mign0tta", - "mignotta", - "minch1a", - "minchia", - "mist", - "musch1", - "muschi", - "n1gger", - "neger", - "negr0", - "negre", - "negro", - "nerch1a", - "nerchia", - "nigger", - "orgasm", - "p00p", - "p011a", - "p01la", - "p0l1a", - "p0lla", - "p0mp1n0", - "p0mp1no", - "p0mpin0", - "p0mpino", - "p0op", - "p0rca", - "p0rn", - "p0rra", - "p0uff1asse", - "p0uffiasse", - "p1p1", - "p1pi", - "p1r1a", - "p1rla", - "p1sc10", - "p1sc1o", - "p1sci0", - "p1scio", - "p1sser", - "pa11e", - "pa1le", - "pal1e", - "palle", - "pane1e1r0", - "pane1e1ro", - "pane1eir0", - "pane1eiro", - "panele1r0", - "panele1ro", - "paneleir0", - "paneleiro", - "patakha", - "pec0r1na", - "pec0rina", - "pecor1na", - "pecorina", - "pen1s", - "pendej0", - "pendejo", - "penis", - "pip1", - "pipi", - "pir1a", - "pirla", - "pisc10", - "pisc1o", - "pisci0", - "piscio", - "pisser", - "po0p", - "po11a", - "po1la", - "pol1a", - "polla", - "pomp1n0", - "pomp1no", - "pompin0", - "pompino", - "poop", - "porca", - "porn", - "porra", - "pouff1asse", - "pouffiasse", - "pr1ck", - "prick", - "pussy", - "put1za", - "puta", - "puta1n", - "putain", - "pute", - "putiza", - "puttana", - "queca", - "r0mp1ba11e", - "r0mp1ba1le", - "r0mp1bal1e", - "r0mp1balle", - "r0mpiba11e", - "r0mpiba1le", - "r0mpibal1e", - "r0mpiballe", - "rand1", - "randi", - "rape", - "recch10ne", - "recch1one", - "recchi0ne", - "recchione", - "retard", - "romp1ba11e", - "romp1ba1le", - "romp1bal1e", - "romp1balle", - "rompiba11e", - "rompiba1le", - "rompibal1e", - "rompiballe", - "ruff1an0", - "ruff1ano", - "ruffian0", - "ruffiano", - "s1ut", - "sa10pe", - "sa1aud", - "sa1ope", - "sacanagem", - "sal0pe", - "salaud", - "salope", - "saugnapf", - "sb0rr0ne", - "sb0rra", - "sb0rrone", - "sbattere", - "sbatters1", - "sbattersi", - "sborr0ne", - "sborra", - "sborrone", - "sc0pare", - "sc0pata", - "sch1ampe", - "sche1se", - "sche1sse", - "scheise", - "scheisse", - "schlampe", - "schwachs1nn1g", - "schwachs1nnig", - "schwachsinn1g", - "schwachsinnig", - "schwanz", - "scopare", - "scopata", - "sexy", - "sh1t", - "shit", - "slut", - "sp0mp1nare", - "sp0mpinare", - "spomp1nare", - "spompinare", - "str0nz0", - "str0nza", - "str0nzo", - "stronz0", - "stronza", - "stronzo", - "stup1d", - "stupid", - "succh1am1", - "succh1ami", - "succhiam1", - "succhiami", - "sucker", - "t0pa", - "tapette", - "test1c1e", - "test1cle", - "testic1e", - "testicle", - "tette", - "topa", - "tr01a", - "tr0ia", - "tr0mbare", - "tr1ng1er", - "tr1ngler", - "tring1er", - "tringler", - "tro1a", - "troia", - "trombare", - "turd", - "twat", - "vaffancu10", - "vaffancu1o", - "vaffancul0", - "vaffanculo", - "vag1na", - "vagina", - "verdammt", - "verga", - "w1chsen", - "wank", - "wichsen", - "x0ch0ta", - "x0chota", - "xana", - "xoch0ta", - "xochota", - "z0cc01a", - "z0cc0la", - "z0cco1a", - "z0ccola", - "z1z1", - "z1zi", - "ziz1", - "zizi", - "zocc01a", - "zocc0la", - "zocco1a", - "zoccola").collect(Collectors.toSet())); + public static final Set DEFAULT_BLOCK_LIST = + Collections.unmodifiableSet( + Stream + .of( + "1d10t", + "1d1ot", + "1di0t", + "1diot", + "1eccacu10", + "1eccacu1o", + "1eccacul0", + "1eccaculo", + "1mbec11e", + "1mbec1le", + "1mbeci1e", + "1mbecile", + "a11upat0", + "a11upato", + "a1lupat0", + "a1lupato", + "aand", + "ah01e", + "ah0le", + "aho1e", + "ahole", + "al1upat0", + "al1upato", + "allupat0", + "allupato", + "ana1", + "ana1e", + "anal", + "anale", + "anus", + "arrapat0", + "arrapato", + "arsch", + "arse", + "ass", + "b00b", + "b00be", + "b01ata", + "b0ceta", + "b0iata", + "b0ob", + "b0obe", + "b0sta", + "b1tch", + "b1te", + "b1tte", + "ba1atkar", + "balatkar", + "bastard0", + "bastardo", + "batt0na", + "battona", + "bitch", + "bite", + "bitte", + "bo0b", + "bo0be", + "bo1ata", + "boceta", + "boiata", + "boob", + "boobe", + "bosta", + "bran1age", + "bran1er", + "bran1ette", + "bran1eur", + "bran1euse", + "branlage", + "branler", + "branlette", + "branleur", + "branleuse", + "c0ck", + "c0g110ne", + "c0g11one", + "c0g1i0ne", + "c0g1ione", + "c0gl10ne", + "c0gl1one", + "c0gli0ne", + "c0glione", + "c0na", + "c0nnard", + "c0nnasse", + "c0nne", + "c0u111es", + "c0u11les", + "c0u1l1es", + "c0u1lles", + "c0ui11es", + "c0ui1les", + "c0uil1es", + "c0uilles", + "c11t", + "c11t0", + "c11to", + "c1it", + "c1it0", + "c1ito", + "cabr0n", + "cabra0", + "cabrao", + "cabron", + "caca", + "cacca", + "cacete", + "cagante", + "cagar", + "cagare", + "cagna", + "cara1h0", + "cara1ho", + "caracu10", + "caracu1o", + "caracul0", + "caraculo", + "caralh0", + "caralho", + "cazz0", + "cazz1mma", + "cazzata", + "cazzimma", + "cazzo", + "ch00t1a", + "ch00t1ya", + "ch00tia", + "ch00tiya", + "ch0d", + "ch0ot1a", + "ch0ot1ya", + "ch0otia", + "ch0otiya", + "ch1asse", + "ch1avata", + "ch1er", + "ch1ng0", + "ch1ngadaz0s", + "ch1ngadazos", + "ch1ngader1ta", + "ch1ngaderita", + "ch1ngar", + "ch1ngo", + "ch1ngues", + "ch1nk", + "chatte", + "chiasse", + "chiavata", + "chier", + "ching0", + "chingadaz0s", + "chingadazos", + "chingader1ta", + "chingaderita", + "chingar", + "chingo", + "chingues", + "chink", + "cho0t1a", + "cho0t1ya", + "cho0tia", + "cho0tiya", + "chod", + "choot1a", + "choot1ya", + "chootia", + "chootiya", + "cl1t", + "cl1t0", + "cl1to", + "clit", + "clit0", + "clito", + "cock", + "cog110ne", + "cog11one", + "cog1i0ne", + "cog1ione", + "cogl10ne", + "cogl1one", + "cogli0ne", + "coglione", + "cona", + "connard", + "connasse", + "conne", + "cou111es", + "cou11les", + "cou1l1es", + "cou1lles", + "coui11es", + "coui1les", + "couil1es", + "couilles", + "cracker", + "crap", + "cu10", + "cu1att0ne", + "cu1attone", + "cu1er0", + "cu1ero", + "cu1o", + "cul0", + "culatt0ne", + "culattone", + "culer0", + "culero", + "culo", + "cum", + "cunt", + "d11d0", + "d11do", + "d1ck", + "d1ld0", + "d1ldo", + "damn", + "de1ch", + "deich", + "depp", + "di1d0", + "di1do", + "dick", + "dild0", + "dildo", + "dyke", + "encu1e", + "encule", + "enema", + "enf01re", + "enf0ire", + "enfo1re", + "enfoire", + "estup1d0", + "estup1do", + "estupid0", + "estupido", + "etr0n", + "etron", + "f0da", + "f0der", + "f0ttere", + "f0tters1", + "f0ttersi", + "f0tze", + "f0utre", + "f1ca", + "f1cker", + "f1ga", + "fag", + "fica", + "ficker", + "figa", + "foda", + "foder", + "fottere", + "fotters1", + "fottersi", + "fotze", + "foutre", + "fr0c10", + "fr0c1o", + "fr0ci0", + "fr0cio", + "fr0sc10", + "fr0sc1o", + "fr0sci0", + "fr0scio", + "froc10", + "froc1o", + "froci0", + "frocio", + "frosc10", + "frosc1o", + "frosci0", + "froscio", + "fuck", + "g00", + "g0o", + "g0u1ne", + "g0uine", + "gandu", + "go0", + "goo", + "gou1ne", + "gouine", + "gr0gnasse", + "grognasse", + "haram1", + "harami", + "haramzade", + "hund1n", + "hundin", + "id10t", + "id1ot", + "idi0t", + "idiot", + "imbec11e", + "imbec1le", + "imbeci1e", + "imbecile", + "j1zz", + "jerk", + "jizz", + "k1ke", + "kam1ne", + "kamine", + "kike", + "leccacu10", + "leccacu1o", + "leccacul0", + "leccaculo", + "m1erda", + "m1gn0tta", + "m1gnotta", + "m1nch1a", + "m1nchia", + "m1st", + "mam0n", + "mamahuev0", + "mamahuevo", + "mamon", + "masturbat10n", + "masturbat1on", + "masturbate", + "masturbati0n", + "masturbation", + "merd0s0", + "merd0so", + "merda", + "merde", + "merdos0", + "merdoso", + "mierda", + "mign0tta", + "mignotta", + "minch1a", + "minchia", + "mist", + "musch1", + "muschi", + "n1gger", + "neger", + "negr0", + "negre", + "negro", + "nerch1a", + "nerchia", + "nigger", + "orgasm", + "p00p", + "p011a", + "p01la", + "p0l1a", + "p0lla", + "p0mp1n0", + "p0mp1no", + "p0mpin0", + "p0mpino", + "p0op", + "p0rca", + "p0rn", + "p0rra", + "p0uff1asse", + "p0uffiasse", + "p1p1", + "p1pi", + "p1r1a", + "p1rla", + "p1sc10", + "p1sc1o", + "p1sci0", + "p1scio", + "p1sser", + "pa11e", + "pa1le", + "pal1e", + "palle", + "pane1e1r0", + "pane1e1ro", + "pane1eir0", + "pane1eiro", + "panele1r0", + "panele1ro", + "paneleir0", + "paneleiro", + "patakha", + "pec0r1na", + "pec0rina", + "pecor1na", + "pecorina", + "pen1s", + "pendej0", + "pendejo", + "penis", + "pip1", + "pipi", + "pir1a", + "pirla", + "pisc10", + "pisc1o", + "pisci0", + "piscio", + "pisser", + "po0p", + "po11a", + "po1la", + "pol1a", + "polla", + "pomp1n0", + "pomp1no", + "pompin0", + "pompino", + "poop", + "porca", + "porn", + "porra", + "pouff1asse", + "pouffiasse", + "pr1ck", + "prick", + "pussy", + "put1za", + "puta", + "puta1n", + "putain", + "pute", + "putiza", + "puttana", + "queca", + "r0mp1ba11e", + "r0mp1ba1le", + "r0mp1bal1e", + "r0mp1balle", + "r0mpiba11e", + "r0mpiba1le", + "r0mpibal1e", + "r0mpiballe", + "rand1", + "randi", + "rape", + "recch10ne", + "recch1one", + "recchi0ne", + "recchione", + "retard", + "romp1ba11e", + "romp1ba1le", + "romp1bal1e", + "romp1balle", + "rompiba11e", + "rompiba1le", + "rompibal1e", + "rompiballe", + "ruff1an0", + "ruff1ano", + "ruffian0", + "ruffiano", + "s1ut", + "sa10pe", + "sa1aud", + "sa1ope", + "sacanagem", + "sal0pe", + "salaud", + "salope", + "saugnapf", + "sb0rr0ne", + "sb0rra", + "sb0rrone", + "sbattere", + "sbatters1", + "sbattersi", + "sborr0ne", + "sborra", + "sborrone", + "sc0pare", + "sc0pata", + "sch1ampe", + "sche1se", + "sche1sse", + "scheise", + "scheisse", + "schlampe", + "schwachs1nn1g", + "schwachs1nnig", + "schwachsinn1g", + "schwachsinnig", + "schwanz", + "scopare", + "scopata", + "sexy", + "sh1t", + "shit", + "slut", + "sp0mp1nare", + "sp0mpinare", + "spomp1nare", + "spompinare", + "str0nz0", + "str0nza", + "str0nzo", + "stronz0", + "stronza", + "stronzo", + "stup1d", + "stupid", + "succh1am1", + "succh1ami", + "succhiam1", + "succhiami", + "sucker", + "t0pa", + "tapette", + "test1c1e", + "test1cle", + "testic1e", + "testicle", + "tette", + "topa", + "tr01a", + "tr0ia", + "tr0mbare", + "tr1ng1er", + "tr1ngler", + "tring1er", + "tringler", + "tro1a", + "troia", + "trombare", + "turd", + "twat", + "vaffancu10", + "vaffancu1o", + "vaffancul0", + "vaffanculo", + "vag1na", + "vagina", + "verdammt", + "verga", + "w1chsen", + "wank", + "wichsen", + "x0ch0ta", + "x0chota", + "xana", + "xoch0ta", + "xochota", + "z0cc01a", + "z0cc0la", + "z0cco1a", + "z0ccola", + "z1z1", + "z1zi", + "ziz1", + "zizi", + "zocc01a", + "zocc0la", + "zocco1a", + "zoccola" + ) + .collect(Collectors.toSet()) + ); private String alphabet = DEFAULT_ALPHABET; private int minLength = DEFAULT_MIN_LENGTH; @@ -878,7 +926,8 @@ public Builder minLength(final int minLength) { */ public Builder blockList(final Set blockList) { if (blockList != null) { - this.blockList = Collections.unmodifiableSet(new HashSet<>(blockList)); + this.blockList = + Collections.unmodifiableSet(new HashSet<>(blockList)); } return this; } diff --git a/src/test/java/org/sqids/AlphabetTests.java b/src/test/java/org/sqids/AlphabetTests.java index 4872f71..8c78c57 100644 --- a/src/test/java/org/sqids/AlphabetTests.java +++ b/src/test/java/org/sqids/AlphabetTests.java @@ -2,16 +2,14 @@ import java.util.Arrays; import java.util.List; - import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Test; public class AlphabetTests { + @Test public void simpleAlphabet() { - Sqids sqids = Sqids.builder() - .alphabet("0123456789abcdef") - .build(); + Sqids sqids = Sqids.builder().alphabet("0123456789abcdef").build(); List numbers = Arrays.asList(1L, 2L, 3L); String id = "489158"; Assertions.assertEquals(sqids.encode(numbers), id); @@ -20,41 +18,39 @@ public void simpleAlphabet() { @Test public void shortAlphabet() { - Sqids sqids = Sqids.builder() - .alphabet("abc") - .build(); + Sqids sqids = Sqids.builder().alphabet("abc").build(); List numbers = Arrays.asList(1L, 2L, 3L); Assertions.assertEquals(sqids.decode(sqids.encode(numbers)), numbers); } @Test public void specialCharsAlphabet() { - Sqids sqids = Sqids.builder() - .alphabet(".\\?") - .build(); + Sqids sqids = Sqids.builder().alphabet(".\\?").build(); List numbers = Arrays.asList(1L, 2L, 3L); Assertions.assertEquals(sqids.decode(sqids.encode(numbers)), numbers); } @Test public void multibyteCharacters() { - Assertions.assertThrows(IllegalArgumentException.class, () -> Sqids.builder() - .alphabet("ë1092") - .build()); + Assertions.assertThrows( + IllegalArgumentException.class, + () -> Sqids.builder().alphabet("ë1092").build() + ); } @Test public void repeatingAlphabetCharacters() { - Assertions.assertThrows(IllegalArgumentException.class, () -> Sqids.builder() - .alphabet("aabcdefg") - .build()); + Assertions.assertThrows( + IllegalArgumentException.class, + () -> Sqids.builder().alphabet("aabcdefg").build() + ); } @Test public void tooShortOfAnAlphabet() { - Assertions.assertThrows(IllegalArgumentException.class, () -> Sqids.builder() - .alphabet("ab") - .build()); + Assertions.assertThrows( + IllegalArgumentException.class, + () -> Sqids.builder().alphabet("ab").build() + ); } - } diff --git a/src/test/java/org/sqids/BlockListTests.java b/src/test/java/org/sqids/BlockListTests.java index 96bf991..c03a2c1 100644 --- a/src/test/java/org/sqids/BlockListTests.java +++ b/src/test/java/org/sqids/BlockListTests.java @@ -3,15 +3,14 @@ import java.util.Arrays; import java.util.HashSet; import java.util.List; - import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Test; public class BlockListTests { + @Test public void blockList() { - Sqids sqids = Sqids.builder() - .build(); + Sqids sqids = Sqids.builder().build(); List numbers = Arrays.asList(4572721L); Assertions.assertEquals(sqids.decode("aho1e"), numbers); Assertions.assertEquals(sqids.encode(numbers), "JExTR"); @@ -19,9 +18,7 @@ public void blockList() { @Test public void emptyBlockList() { - Sqids sqids = Sqids.builder() - .blockList(new HashSet<>()) - .build(); + Sqids sqids = Sqids.builder().blockList(new HashSet<>()).build(); List numbers = Arrays.asList(4572721L); Assertions.assertEquals(sqids.decode("aho1e"), numbers); Assertions.assertEquals(sqids.encode(numbers), "aho1e"); @@ -29,9 +26,10 @@ public void emptyBlockList() { @Test public void nonEmptyBlockList() { - Sqids sqids = Sqids.builder() - .blockList(new HashSet<>(Arrays.asList("ArUO"))) - .build(); + Sqids sqids = Sqids + .builder() + .blockList(new HashSet<>(Arrays.asList("ArUO"))) + .build(); List numbers = Arrays.asList(4572721L); Assertions.assertEquals(sqids.decode("aho1e"), numbers); Assertions.assertEquals(sqids.encode(numbers), "aho1e"); @@ -44,15 +42,20 @@ public void nonEmptyBlockList() { @Test public void encodeBlockList() { - Sqids sqids = Sqids.builder() - .blockList(new HashSet<>(Arrays.asList( + Sqids sqids = Sqids + .builder() + .blockList( + new HashSet<>( + Arrays.asList( "JSwXFaosAN", // normal result of 1st encoding, let's block that word on purpose "OCjV9JK64o", // result of 2nd encoding "rBHf", // result of 3rd encoding is `4rBHfOiqd3`, let's block a substring "79SM", // result of 4th encoding is `dyhgw479SM`, let's block the postfix "7tE6" // result of 4th encoding is `7tE6jdAHLe`, let's block the prefix - ))) - .build(); + ) + ) + ) + .build(); List numbers = Arrays.asList(1000000L, 2000000L); Assertions.assertEquals(sqids.encode(numbers), "1aYeB7bRUt"); Assertions.assertEquals(sqids.decode("1aYeB7bRUt"), numbers); @@ -60,15 +63,20 @@ public void encodeBlockList() { @Test public void decodeBlockList() { - Sqids sqids = Sqids.builder() - .blockList(new HashSet<>(Arrays.asList( + Sqids sqids = Sqids + .builder() + .blockList( + new HashSet<>( + Arrays.asList( "86Rf07", "se8ojk", "ARsz1p", "Q8AI49", "5sQRZO" - ))) - .build(); + ) + ) + ) + .build(); List numbers = Arrays.asList(1L, 2L, 3L); Assertions.assertEquals(sqids.decode("86Rf07"), numbers); Assertions.assertEquals(sqids.decode("se8ojk"), numbers); @@ -79,19 +87,21 @@ public void decodeBlockList() { @Test public void shortBlockList() { - Sqids sqids = Sqids.builder() - .blockList(new HashSet<>(Arrays.asList("pnd"))) - .build(); + Sqids sqids = Sqids + .builder() + .blockList(new HashSet<>(Arrays.asList("pnd"))) + .build(); List numbers = Arrays.asList(1000L); Assertions.assertEquals(sqids.decode(sqids.encode(numbers)), numbers); } @Test public void lowercaseBlockList() { - Sqids sqids = Sqids.builder() - .alphabet("ABCDEFGHIJKLMNOPQRSTUVWXYZ") - .blockList(new HashSet<>(Arrays.asList("sxnzkl"))) - .build(); + Sqids sqids = Sqids + .builder() + .alphabet("ABCDEFGHIJKLMNOPQRSTUVWXYZ") + .blockList(new HashSet<>(Arrays.asList("sxnzkl"))) + .build(); List numbers = Arrays.asList(1L, 2L, 3L); Assertions.assertEquals(sqids.encode(numbers), "IBSHOZ"); Assertions.assertEquals(sqids.decode("IBSHOZ"), numbers); @@ -99,14 +109,15 @@ public void lowercaseBlockList() { @Test public void maxBlockList() { - Sqids sqids = Sqids.builder() - .alphabet("abc") - .minLength(3) - .blockList(new HashSet<>(Arrays.asList( - "cab", - "abc", - "bca"))) - .build(); - Assertions.assertThrows(RuntimeException.class, () -> sqids.encode(Arrays.asList(0L))); + Sqids sqids = Sqids + .builder() + .alphabet("abc") + .minLength(3) + .blockList(new HashSet<>(Arrays.asList("cab", "abc", "bca"))) + .build(); + Assertions.assertThrows( + RuntimeException.class, + () -> sqids.encode(Arrays.asList(0L)) + ); } } diff --git a/src/test/java/org/sqids/EncodeTests.java b/src/test/java/org/sqids/EncodeTests.java index f66c070..3163ac5 100644 --- a/src/test/java/org/sqids/EncodeTests.java +++ b/src/test/java/org/sqids/EncodeTests.java @@ -5,11 +5,11 @@ import java.util.HashMap; import java.util.List; import java.util.Map; - import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Test; public class EncodeTests { + private final Sqids sqids = Sqids.builder().build(); @Test @@ -23,17 +23,18 @@ public void simple() { @Test public void differentInputs() { List numbers = Arrays.asList( - 0L, - 0L, - 0L, - 1L, - 2L, - 3L, - 100L, - 1000L, - 100000L, - 1000000L, - Long.MAX_VALUE); + 0L, + 0L, + 0L, + 1L, + 2L, + 3L, + 100L, + 1000L, + 100000L, + 1000000L, + Long.MAX_VALUE + ); Assertions.assertEquals(sqids.decode(sqids.encode(numbers)), numbers); } @@ -86,12 +87,107 @@ public void incrementalNumbers() { @Test public void multiInput() { List numbers = Arrays.asList( - 0L, 1L, 2L, 3L, 4L, 5L, 6L, 7L, 8L, 9L, 10L, 11L, 12L, 13L, 14L, 15L, 16L, 17L, 18L, 19L, 20L, - 21L, 22L, 23L, 24L, 25L, 26L, 27L, 28L, 29L, 30L, 31L, 32L, 33L, 34L, 35L, 36L, 37L, 38L, - 39L, 40L, 41L, 42L, 43L, 44L, 45L, 46L, 47L, 48L, 49L, 50L, 51L, 52L, 53L, 54L, 55L, 56L, - 57L, 58L, 59L, 60L, 61L, 62L, 63L, 64L, 65L, 66L, 67L, 68L, 69L, 70L, 71L, 72L, 73L, 74L, - 75L, 76L, 77L, 78L, 79L, 80L, 81L, 82L, 83L, 84L, 85L, 86L, 87L, 88L, 89L, 90L, 91L, 92L, - 93L, 94L, 95L, 96L, 97L, 98L, 99L); + 0L, + 1L, + 2L, + 3L, + 4L, + 5L, + 6L, + 7L, + 8L, + 9L, + 10L, + 11L, + 12L, + 13L, + 14L, + 15L, + 16L, + 17L, + 18L, + 19L, + 20L, + 21L, + 22L, + 23L, + 24L, + 25L, + 26L, + 27L, + 28L, + 29L, + 30L, + 31L, + 32L, + 33L, + 34L, + 35L, + 36L, + 37L, + 38L, + 39L, + 40L, + 41L, + 42L, + 43L, + 44L, + 45L, + 46L, + 47L, + 48L, + 49L, + 50L, + 51L, + 52L, + 53L, + 54L, + 55L, + 56L, + 57L, + 58L, + 59L, + 60L, + 61L, + 62L, + 63L, + 64L, + 65L, + 66L, + 67L, + 68L, + 69L, + 70L, + 71L, + 72L, + 73L, + 74L, + 75L, + 76L, + 77L, + 78L, + 79L, + 80L, + 81L, + 82L, + 83L, + 84L, + 85L, + 86L, + 87L, + 88L, + 89L, + 90L, + 91L, + 92L, + 93L, + 94L, + 95L, + 96L, + 97L, + 98L, + 99L + ); Assertions.assertEquals(sqids.decode(sqids.encode(numbers)), numbers); } @@ -115,7 +211,13 @@ public void decodeInvalidCharacter() { @Test public void encodeOutOfRangeNumbers() { - Assertions.assertThrows(RuntimeException.class, () -> sqids.encode(Arrays.asList(-1L))); - Assertions.assertThrows(RuntimeException.class, () -> sqids.encode(Arrays.asList(Long.MAX_VALUE + 1))); + Assertions.assertThrows( + RuntimeException.class, + () -> sqids.encode(Arrays.asList(-1L)) + ); + Assertions.assertThrows( + RuntimeException.class, + () -> sqids.encode(Arrays.asList(Long.MAX_VALUE + 1)) + ); } } diff --git a/src/test/java/org/sqids/MinLengthTests.java b/src/test/java/org/sqids/MinLengthTests.java index c67d02a..5c6f926 100644 --- a/src/test/java/org/sqids/MinLengthTests.java +++ b/src/test/java/org/sqids/MinLengthTests.java @@ -5,20 +5,19 @@ import java.util.HashMap; import java.util.List; import java.util.Map; - import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Test; public class MinLengthTests { + private final int minLength = Sqids.Builder.DEFAULT_ALPHABET.length(); @Test public void simple() { - Sqids sqids = Sqids.builder() - .minLength(minLength) - .build(); + Sqids sqids = Sqids.builder().minLength(minLength).build(); List numbers = Arrays.asList(1L, 2L, 3L); - String id = "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTM"; + String id = + "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTM"; Assertions.assertEquals(sqids.encode(numbers), id); Assertions.assertEquals(sqids.decode(id), numbers); } @@ -36,16 +35,26 @@ public void incremental() { put(11, "86Rf07xd4zB"); put(12, "86Rf07xd4zBm"); put(13, "86Rf07xd4zBmi"); - put(minLength + 0, "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTM"); - put(minLength + 1, "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTMy"); - put(minLength + 2, "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTMyf"); - put(minLength + 3, "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTMyf1"); + put( + minLength + 0, + "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTM" + ); + put( + minLength + 1, + "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTMy" + ); + put( + minLength + 2, + "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTMyf" + ); + put( + minLength + 3, + "86Rf07xd4zBmiJXQG6otHEbew02c3PWsUOLZxADhCpKj7aVFv9I8RquYrNlSTMyf1" + ); } }; for (Integer minLength : ids.keySet()) { - Sqids sqids = Sqids.builder() - .minLength(minLength) - .build(); + Sqids sqids = Sqids.builder().minLength(minLength).build(); String id = ids.get(minLength); Assertions.assertEquals(sqids.encode(numbers), id); Assertions.assertEquals(sqids.decode(id), numbers); @@ -54,21 +63,49 @@ public void incremental() { @Test public void incrementalNumbers() { - Sqids sqids = Sqids.builder() - .minLength(minLength) - .build(); + Sqids sqids = Sqids.builder().minLength(minLength).build(); Map> ids = new HashMap>() { { - put("SvIzsqYMyQwI3GWgJAe17URxX8V924Co0DaTZLtFjHriEn5bPhcSkfmvOslpBu", Arrays.asList(0L, 0L)); - put("n3qafPOLKdfHpuNw3M61r95svbeJGk7aAEgYn4WlSjXURmF8IDqZBy0CT2VxQc", Arrays.asList(0L, 1L)); - put("tryFJbWcFMiYPg8sASm51uIV93GXTnvRzyfLleh06CpodJD42B7OraKtkQNxUZ", Arrays.asList(0L, 2L)); - put("eg6ql0A3XmvPoCzMlB6DraNGcWSIy5VR8iYup2Qk4tjZFKe1hbwfgHdUTsnLqE", Arrays.asList(0L, 3L)); - put("rSCFlp0rB2inEljaRdxKt7FkIbODSf8wYgTsZM1HL9JzN35cyoqueUvVWCm4hX", Arrays.asList(0L, 4L)); - put("sR8xjC8WQkOwo74PnglH1YFdTI0eaf56RGVSitzbjuZ3shNUXBrqLxEJyAmKv2", Arrays.asList(0L, 5L)); - put("uY2MYFqCLpgx5XQcjdtZK286AwWV7IBGEfuS9yTmbJvkzoUPeYRHr4iDs3naN0", Arrays.asList(0L, 6L)); - put("74dID7X28VLQhBlnGmjZrec5wTA1fqpWtK4YkaoEIM9SRNiC3gUJH0OFvsPDdy", Arrays.asList(0L, 7L)); - put("30WXpesPhgKiEI5RHTY7xbB1GnytJvXOl2p0AcUjdF6waZDo9Qk8VLzMuWrqCS", Arrays.asList(0L, 8L)); - put("moxr3HqLAK0GsTND6jowfZz3SUx7cQ8aC54Pl1RbIvFXmEJuBMYVeW9yrdOtin", Arrays.asList(0L, 9L)); + put( + "SvIzsqYMyQwI3GWgJAe17URxX8V924Co0DaTZLtFjHriEn5bPhcSkfmvOslpBu", + Arrays.asList(0L, 0L) + ); + put( + "n3qafPOLKdfHpuNw3M61r95svbeJGk7aAEgYn4WlSjXURmF8IDqZBy0CT2VxQc", + Arrays.asList(0L, 1L) + ); + put( + "tryFJbWcFMiYPg8sASm51uIV93GXTnvRzyfLleh06CpodJD42B7OraKtkQNxUZ", + Arrays.asList(0L, 2L) + ); + put( + "eg6ql0A3XmvPoCzMlB6DraNGcWSIy5VR8iYup2Qk4tjZFKe1hbwfgHdUTsnLqE", + Arrays.asList(0L, 3L) + ); + put( + "rSCFlp0rB2inEljaRdxKt7FkIbODSf8wYgTsZM1HL9JzN35cyoqueUvVWCm4hX", + Arrays.asList(0L, 4L) + ); + put( + "sR8xjC8WQkOwo74PnglH1YFdTI0eaf56RGVSitzbjuZ3shNUXBrqLxEJyAmKv2", + Arrays.asList(0L, 5L) + ); + put( + "uY2MYFqCLpgx5XQcjdtZK286AwWV7IBGEfuS9yTmbJvkzoUPeYRHr4iDs3naN0", + Arrays.asList(0L, 6L) + ); + put( + "74dID7X28VLQhBlnGmjZrec5wTA1fqpWtK4YkaoEIM9SRNiC3gUJH0OFvsPDdy", + Arrays.asList(0L, 7L) + ); + put( + "30WXpesPhgKiEI5RHTY7xbB1GnytJvXOl2p0AcUjdF6waZDo9Qk8VLzMuWrqCS", + Arrays.asList(0L, 8L) + ); + put( + "moxr3HqLAK0GsTND6jowfZz3SUx7cQ8aC54Pl1RbIvFXmEJuBMYVeW9yrdOtin", + Arrays.asList(0L, 9L) + ); } }; for (String id : ids.keySet()) { @@ -81,18 +118,18 @@ public void incrementalNumbers() { @Test public void minLengths() { List minLengths = Arrays.asList(0, 1, 5, 10, minLength); - List> numbers = new ArrayList>() {{ - add(Arrays.asList(0L)); - add(Arrays.asList(0L, 0L, 0L, 0L, 0L)); - add(Arrays.asList(1L, 2L, 3L, 4L, 5L, 6L, 7L, 8L, 9L, 10L)); - add(Arrays.asList(100L, 200L, 300L)); - add(Arrays.asList(1000L, 2000L, 30000L)); - add(Arrays.asList((long) Integer.MAX_VALUE)); - }}; + List> numbers = new ArrayList>() { + { + add(Arrays.asList(0L)); + add(Arrays.asList(0L, 0L, 0L, 0L, 0L)); + add(Arrays.asList(1L, 2L, 3L, 4L, 5L, 6L, 7L, 8L, 9L, 10L)); + add(Arrays.asList(100L, 200L, 300L)); + add(Arrays.asList(1000L, 2000L, 30000L)); + add(Arrays.asList((long) Integer.MAX_VALUE)); + } + }; for (Integer minLength : minLengths) { - Sqids sqids = Sqids.builder() - .minLength(minLength) - .build(); + Sqids sqids = Sqids.builder().minLength(minLength).build(); for (List number : numbers) { String id = sqids.encode(number); Assertions.assertTrue(id.length() >= minLength); @@ -104,11 +141,13 @@ public void minLengths() { @Test public void encodeOutOfRangeNumbers() { int minLengthLimit = 255; - Assertions.assertThrows(RuntimeException.class, () -> Sqids.builder() - .minLength(-1) - .build()); - Assertions.assertThrows(RuntimeException.class, () -> Sqids.builder() - .minLength(minLengthLimit + 1) - .build()); + Assertions.assertThrows( + RuntimeException.class, + () -> Sqids.builder().minLength(-1).build() + ); + Assertions.assertThrows( + RuntimeException.class, + () -> Sqids.builder().minLength(minLengthLimit + 1).build() + ); } } From f6c09dd880baebf50171432b79f98df53e8fa479 Mon Sep 17 00:00:00 2001 From: Rob Hanlon <69870+robhanlon22@users.noreply.github.com> Date: Thu, 30 Nov 2023 08:53:18 -0800 Subject: [PATCH 2/2] greclipse is buggy, remove it --- .greclipse.properties | 4 ---- build.gradle | 4 ---- 2 files changed, 8 deletions(-) delete mode 100644 .greclipse.properties diff --git a/.greclipse.properties b/.greclipse.properties deleted file mode 100644 index 812ab1b..0000000 --- a/.greclipse.properties +++ /dev/null @@ -1,4 +0,0 @@ -groovy.formatter.remove.unnecessary.semicolons = true -org.eclipse.jdt.core.formatter.indent_empty_lines = false -org.eclipse.jdt.core.formatter.tabulation.char = space -org.eclipse.jdt.core.formatter.tabulation.size = 4 diff --git a/build.gradle b/build.gradle index 8e633fc..880da69 100644 --- a/build.gradle +++ b/build.gradle @@ -110,10 +110,6 @@ spotless { .nodeExecutable("${tasks.named(nodeSetup).get().nodeDir.get()}${nodeExec}") .configFile('.prettierrc.yaml') } - - groovyGradle { - greclipse().configFile('.greclipse.properties') - } } tasks.named('spotlessPrettier').configure { task ->