tasks.register('validateAnnotations', ValidateAnnotations) {
	group = 'fabric'
	description = "Validate annotations used in Fabric API code."

	outputs.upToDateWhen { true } // Task has no outputs

	// Only apply to default source directories since there's also generated package-info files.
	source file("src/client/java")
	source file("src/main/java")
	source file("src/testmod/java")
	source file("src/testmodClient/java")
}

tasks.check.dependsOn "validateAnnotations"

abstract class ValidateAnnotations extends SourceTask {
	private static final def API_STATUS_INTERNAL = ~/@ApiStatus\.Internal/
	private static final def ENVIRONMENT = ~/@Environment/

	@TaskAction
	def run() {
		for (def dir in [
					'api',
					'impl',
					'mixin',
					'test'
				]) {
			getSource().matching { include "net/fabricmc/fabric/$dir/" }.forEach {
				if (it.isDirectory()) {
					return
				}

				def contents = it.text

				// @Environment is never allowed
				if (ENVIRONMENT.matcher(contents).find()) {
					throw new RuntimeException("Found @Environment annotation in file: $it")
				}

				// @ApiStatus.Internal is only allowed in api packages (it's auto-generated for impl and mixin packages)
				if (dir != "api") {
					if (API_STATUS_INTERNAL.matcher(contents).find()) {
						throw new RuntimeException("Found @ApiStatus.Internal in implementation file: " + it)
					}
				}
			}
		}
	}
}
