Skip to content

Commit 9be3a81

Browse files
Rafał ChomczykRollczi
andauthored
GH-393 Add implementation for command cooldowns; Fix typo in requirement package name (#393)
* Add implementation for command cooldowns; Fix typo in requirement package name * Fix registration of global scoped validators. * Fix overwriting of validator, in case of same scopes --------- Co-authored-by: Rollczi <[email protected]>
1 parent d0e69d5 commit 9be3a81

File tree

20 files changed

+315
-21
lines changed

20 files changed

+315
-21
lines changed

.github/TODO.md

Lines changed: 9 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -14,17 +14,17 @@ TODO
1414
- [x] @Join String
1515
- [x] @Async @Arg
1616
- [x] @Permission
17-
- [ ] @Arg @Range(min = 1, max = 10) int
17+
- [x] @Arg @Range(min = 1, max = 10) int
1818
- [x] @Flag for booleans
1919
- [ ] @Editor
2020
- [x] @Arg Enum
21-
- [ ] @Arg List<String> // for example text, text, text
22-
- [ ] @Arg Set<T> // for example 1, 4, 5
21+
- [x] @Arg List<String> // for example text, text, text
22+
- [x] @Arg Set<T> // for example 1, 4, 5
2323
- [ ] @Arg Map<K, V> // for example key1=value1, key2=value2 // do wyrzucenia chyba
2424
- [ ] @Suggest
2525
- [ ] @Literal
2626
- [x] @Validate(validator = MyValidator.class)
27-
- [ ] @Cooldown - Określa cza s, przez który użytkownik nie może ponownie użyć danej komendy po jej wykonaniu.
27+
- [x] @Cooldown - Określa cza s, przez który użytkownik nie może ponownie użyć danej komendy po jej wykonaniu.
2828
- [ ] @Cooldown(second = 10, bypass = "myplugin.bypass.cooldown", scope = CooldownScope.GLOBAL)
2929
- [ ] @MaxCalls(second = 10, max = 5)
3030
- [ ] @Delay - Adnotacja ta może być użyta przed metodą, aby określić czas opóźnienia (w milisekundach) przed wykonaniem
@@ -37,19 +37,20 @@ TODO
3737
- [x] @Context
3838
- [ ] .debugger(true)
3939
- [x] .errorHandler()
40-
- [ ] @Arg @Regex("") String
41-
- [ ] @Arg @Regex("[a-zA-Z0-9_]") @Length(min = 3, max = 16) String playerName
40+
- [x] @Arg @Regex("") String
41+
- [x] @Arg @Regex("[a-zA-Z0-9_]") @Length(min = 3, max = 16) String playerName
4242
- [x] Return result handler
4343
- [x] Return result handler remapper
4444
- [x] Support JDA
45-
- [ ] Support Sponge
45+
- [x] Support Sponge
4646
- [x] Support BungeeCord
47-
- [ ] Support Waterfall
47+
- [x] Support Waterfall
4848
- [x] Support Velocity
4949
- [x] Support Bukkit
5050
- [ ] Support Nukkit
5151
- [x] Support Adventure
5252
- [x] Support Paper
53+
- [x] Support Fabric
5354
- [x] Add support to provide other types of arguments by platforms
5455

5556
### This is not a command example. They're just concepts!

litecommands-annotations/src/dev/rollczi/litecommands/annotations/AnnotationProcessorService.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
import dev.rollczi.litecommands.annotations.command.CommandAnnotationProcessor;
99
import dev.rollczi.litecommands.annotations.command.RootCommandAnnotationProcessor;
1010
import dev.rollczi.litecommands.annotations.context.ContextRequirementProcessor;
11+
import dev.rollczi.litecommands.annotations.cooldown.CooldownAnnotationResolver;
1112
import dev.rollczi.litecommands.annotations.description.DescriptionAnnotationResolver;
1213
import dev.rollczi.litecommands.annotations.execute.ExecuteAnnotationResolver;
1314
import dev.rollczi.litecommands.annotations.flag.FlagArgumentProcessor;
@@ -55,6 +56,7 @@ public static <SENDER> AnnotationProcessorService<SENDER> defaultService() {
5556
.register(new PermissionAnnotationResolver<>())
5657
.register(new PermissionsAnnotationResolver<>())
5758
.register(new ValidateAnnotationResolver<>())
59+
.register(new CooldownAnnotationResolver<>())
5860
// argument meta processors
5961
.register(new KeyAnnotationResolver<>())
6062
.register(new QuotedAnnotationProcessor<>())
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
package dev.rollczi.litecommands.annotations.cooldown;
2+
3+
import java.lang.annotation.ElementType;
4+
import java.lang.annotation.Retention;
5+
import java.lang.annotation.RetentionPolicy;
6+
import java.lang.annotation.Target;
7+
import java.time.temporal.ChronoUnit;
8+
9+
@Target({ElementType.TYPE, ElementType.METHOD})
10+
@Retention(RetentionPolicy.RUNTIME)
11+
public @interface Cooldown {
12+
13+
String key();
14+
15+
long count();
16+
17+
ChronoUnit unit();
18+
19+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
package dev.rollczi.litecommands.annotations.cooldown;
2+
3+
import dev.rollczi.litecommands.annotations.AnnotationInvoker;
4+
import dev.rollczi.litecommands.annotations.AnnotationProcessor;
5+
import dev.rollczi.litecommands.cooldown.CooldownContext;
6+
import dev.rollczi.litecommands.meta.Meta;
7+
import java.time.Duration;
8+
9+
public class CooldownAnnotationResolver<SENDER> implements AnnotationProcessor<SENDER> {
10+
11+
@Override
12+
public AnnotationInvoker<SENDER> process(AnnotationInvoker<SENDER> invoker) {
13+
return invoker
14+
.on(Cooldown.class, ((annotation, metaHolder) -> metaHolder.meta()
15+
.put(Meta.COOLDOWN, getCooldownContext(annotation))));
16+
}
17+
18+
private CooldownContext getCooldownContext(Cooldown cooldown) {
19+
return new CooldownContext(cooldown.key(), Duration.of(cooldown.count(), cooldown.unit()));
20+
}
21+
22+
}

litecommands-annotations/src/dev/rollczi/litecommands/annotations/validator/requirment/RequirementAnnotatedValidatorImpl.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
import dev.rollczi.litecommands.invocation.Invocation;
55
import dev.rollczi.litecommands.requirement.Requirement;
66
import dev.rollczi.litecommands.validator.ValidatorResult;
7-
import dev.rollczi.litecommands.validator.requirment.RequirementValidator;
7+
import dev.rollczi.litecommands.validator.requirement.RequirementValidator;
88

99
import java.lang.annotation.Annotation;
1010

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
package dev.rollczi.litecommands.annotations.cooldown;
2+
3+
import static org.junit.jupiter.api.Assertions.assertEquals;
4+
import static org.junit.jupiter.api.Assertions.assertFalse;
5+
6+
import dev.rollczi.litecommands.annotations.LiteTestSpec;
7+
import dev.rollczi.litecommands.annotations.command.Command;
8+
import dev.rollczi.litecommands.annotations.execute.Execute;
9+
import dev.rollczi.litecommands.cooldown.CooldownState;
10+
import java.time.Duration;
11+
import java.time.temporal.ChronoUnit;
12+
import org.awaitility.Awaitility;
13+
import org.junit.jupiter.api.Test;
14+
15+
class CooldownAnnotationTest extends LiteTestSpec {
16+
17+
@Command(name = "test")
18+
@Cooldown(key = "test-cooldown", count = 1, unit = ChronoUnit.SECONDS)
19+
static class TestCommand {
20+
21+
@Execute
22+
void execute() {}
23+
24+
}
25+
26+
@Test
27+
void test() {
28+
platform.execute("test");
29+
30+
CooldownState cooldownState = platform.execute("test")
31+
.assertFailedAs(CooldownState.class);
32+
33+
assertEquals("test-cooldown", cooldownState.getCooldownContext().getKey());
34+
assertEquals(Duration.ofSeconds(1), cooldownState.getCooldownContext().getDuration());
35+
assertFalse(cooldownState.getRemainingDuration().isZero());
36+
37+
Awaitility.await()
38+
.atMost(Duration.ofSeconds(3))
39+
.until(() -> platform.execute("test").isSuccessful());
40+
}
41+
42+
}

litecommands-core/build.gradle.kts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ plugins {
88
}
99

1010
dependencies {
11+
api("net.jodah:expiringmap:0.5.11")
1112
api("org.panda-lang:expressible:1.3.6")
1213
api("org.jetbrains:annotations:24.0.1")
1314
}

litecommands-core/src/dev/rollczi/litecommands/command/executor/CommandExecuteService.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@
2424
import dev.rollczi.litecommands.scheduler.SchedulerPoll;
2525
import dev.rollczi.litecommands.validator.ValidatorResult;
2626
import dev.rollczi.litecommands.validator.ValidatorService;
27-
import dev.rollczi.litecommands.validator.requirment.RequirementValidator;
27+
import dev.rollczi.litecommands.validator.requirement.RequirementValidator;
2828
import dev.rollczi.litecommands.wrapper.Wrap;
2929
import dev.rollczi.litecommands.wrapper.WrapFormat;
3030
import dev.rollczi.litecommands.wrapper.Wrapper;
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
package dev.rollczi.litecommands.cooldown;
2+
3+
import dev.rollczi.litecommands.identifier.Identifier;
4+
import java.util.Objects;
5+
6+
class CooldownCompositeKey {
7+
8+
private final Identifier identifier;
9+
private final String cooldownKey;
10+
11+
public CooldownCompositeKey(Identifier identifier, String cooldownKey) {
12+
this.identifier = identifier;
13+
this.cooldownKey = cooldownKey;
14+
}
15+
16+
public Identifier getIdentifier() {
17+
return identifier;
18+
}
19+
20+
public String getCooldownKey() {
21+
return cooldownKey;
22+
}
23+
24+
@Override
25+
public boolean equals(Object object) {
26+
if (this == object) {
27+
return true;
28+
}
29+
30+
if (object == null || getClass() != object.getClass()) {
31+
return false;
32+
}
33+
34+
CooldownCompositeKey that = (CooldownCompositeKey) object;
35+
return Objects.equals(identifier, that.identifier) && Objects.equals(cooldownKey, that.cooldownKey);
36+
}
37+
38+
@Override
39+
public int hashCode() {
40+
return Objects.hash(identifier, cooldownKey);
41+
}
42+
43+
}
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
package dev.rollczi.litecommands.cooldown;
2+
3+
import java.time.Duration;
4+
5+
public class CooldownContext {
6+
7+
private final String key;
8+
private final Duration duration;
9+
10+
public CooldownContext(String key, Duration duration) {
11+
this.key = key;
12+
this.duration = duration;
13+
}
14+
15+
public String getKey() {
16+
return key;
17+
}
18+
19+
public Duration getDuration() {
20+
return duration;
21+
}
22+
23+
}

0 commit comments

Comments
 (0)