@ngxtm/devkit 3.4.0 → 3.4.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +2 -1
- package/rules/README.md +141 -0
- package/rules/dart/best-practices/SKILL.md +23 -0
- package/rules/dart/language/SKILL.md +52 -0
- package/rules/dart/tooling/SKILL.md +43 -0
- package/rules/dotnet/aspnet-core/SKILL.md +92 -0
- package/rules/dotnet/aspnet-core/references/REFERENCE.md +335 -0
- package/rules/dotnet/best-practices/SKILL.md +101 -0
- package/rules/dotnet/best-practices/references/REFERENCE.md +256 -0
- package/rules/dotnet/blazor/SKILL.md +146 -0
- package/rules/dotnet/blazor/references/REFERENCE.md +392 -0
- package/rules/dotnet/language/SKILL.md +82 -0
- package/rules/dotnet/language/references/REFERENCE.md +222 -0
- package/rules/dotnet/patterns.rule.md +388 -0
- package/rules/dotnet/razor-pages/SKILL.md +124 -0
- package/rules/dotnet/razor-pages/references/REFERENCE.md +321 -0
- package/rules/dotnet/security/SKILL.md +89 -0
- package/rules/dotnet/security/references/REFERENCE.md +295 -0
- package/rules/dotnet/tooling/SKILL.md +92 -0
- package/rules/dotnet/tooling/references/REFERENCE.md +300 -0
- package/rules/flutter/auto-route-navigation/SKILL.md +43 -0
- package/rules/flutter/auto-route-navigation/references/REFERENCE.md +19 -0
- package/rules/flutter/auto-route-navigation/references/router-config.md +62 -0
- package/rules/flutter/bloc-state-management/SKILL.md +64 -0
- package/rules/flutter/bloc-state-management/references/REFERENCE.md +20 -0
- package/rules/flutter/bloc-state-management/references/auth-bloc-example.md +52 -0
- package/rules/flutter/bloc-state-management/references/equatable-usage.md +56 -0
- package/rules/flutter/bloc-state-management/references/property-based-state.md +68 -0
- package/rules/flutter/bloc.rule.md +76 -0
- package/rules/flutter/cicd/SKILL.md +48 -0
- package/rules/flutter/cicd/references/advanced-workflow.md +66 -0
- package/rules/flutter/cicd/references/fastlane.md +139 -0
- package/rules/flutter/cicd/references/github-actions.md +59 -0
- package/rules/flutter/dependency-injection/SKILL.md +42 -0
- package/rules/flutter/dependency-injection/references/REFERENCE.md +15 -0
- package/rules/flutter/dependency-injection/references/modules.md +37 -0
- package/rules/flutter/error-handling/SKILL.md +32 -0
- package/rules/flutter/error-handling/references/REFERENCE.md +19 -0
- package/rules/flutter/error-handling/references/error-mapping.md +31 -0
- package/rules/flutter/feature-based-clean-architecture/SKILL.md +46 -0
- package/rules/flutter/feature-based-clean-architecture/references/REFERENCE.md +14 -0
- package/rules/flutter/feature-based-clean-architecture/references/folder-structure.md +36 -0
- package/rules/flutter/getx-navigation/SKILL.md +70 -0
- package/rules/flutter/getx-navigation/references/app-pages.md +40 -0
- package/rules/flutter/getx-navigation/references/middleware-example.md +29 -0
- package/rules/flutter/getx-state-management/SKILL.md +76 -0
- package/rules/flutter/getx-state-management/references/binding-example.md +32 -0
- package/rules/flutter/getx-state-management/references/reactive-vs-simple.md +39 -0
- package/rules/flutter/go-router-navigation/SKILL.md +57 -0
- package/rules/flutter/idiomatic-flutter/SKILL.md +20 -0
- package/rules/flutter/layer-based-clean-architecture/SKILL.md +50 -0
- package/rules/flutter/layer-based-clean-architecture/references/REFERENCE.md +60 -0
- package/rules/flutter/layer-based-clean-architecture/references/repository-mapping.md +50 -0
- package/rules/flutter/localization/SKILL.md +50 -0
- package/rules/flutter/localization/references/REFERENCE.md +48 -0
- package/rules/flutter/localization/references/sheet-loader.md +33 -0
- package/rules/flutter/navigator-v1-navigation/SKILL.md +71 -0
- package/rules/flutter/navigator-v1-navigation/references/on-generate-route.md +48 -0
- package/rules/flutter/performance/SKILL.md +24 -0
- package/rules/flutter/retrofit-networking/SKILL.md +51 -0
- package/rules/flutter/retrofit-networking/references/REFERENCE.md +19 -0
- package/rules/flutter/retrofit-networking/references/token-refresh.md +40 -0
- package/rules/flutter/riverpod-state-management/SKILL.md +53 -0
- package/rules/flutter/riverpod-state-management/references/architecture.md +124 -0
- package/rules/flutter/riverpod-state-management/references/best-practices.md +89 -0
- package/rules/flutter/riverpod-state-management/references/testing.md +73 -0
- package/rules/flutter/riverpod.rule.md +78 -0
- package/rules/flutter/security/SKILL.md +33 -0
- package/rules/flutter/security/references/REFERENCE.md +15 -0
- package/rules/flutter/security/references/network-security.md +28 -0
- package/rules/flutter/testing/SKILL.md +44 -0
- package/rules/flutter/testing/references/REFERENCE.md +21 -0
- package/rules/flutter/testing/references/bloc-testing.md +38 -0
- package/rules/flutter/testing/references/integration-testing.md +128 -0
- package/rules/flutter/testing/references/robot-pattern.md +82 -0
- package/rules/flutter/testing/references/unit-testing.md +130 -0
- package/rules/flutter/testing/references/widget-testing.md +120 -0
- package/rules/flutter/widgets/SKILL.md +37 -0
- package/rules/golang/chi-router/SKILL.md +219 -0
- package/rules/golang/chi-router/references/REFERENCE.md +13 -0
- package/rules/golang/chi-router/references/routing-patterns.md +205 -0
- package/rules/golang/cobra-cli/SKILL.md +227 -0
- package/rules/golang/cobra-cli/references/REFERENCE.md +13 -0
- package/rules/golang/cobra-cli/references/command-patterns.md +224 -0
- package/rules/golang/core/SKILL.md +210 -0
- package/rules/golang/core/references/REFERENCE.md +14 -0
- package/rules/golang/core/references/concurrency-patterns.md +114 -0
- package/rules/golang/core/references/error-handling.md +87 -0
- package/rules/golang/echo-framework/SKILL.md +215 -0
- package/rules/golang/echo-framework/references/REFERENCE.md +14 -0
- package/rules/golang/echo-framework/references/middleware-patterns.md +141 -0
- package/rules/golang/echo-framework/references/routing-patterns.md +140 -0
- package/rules/golang/ent-orm/SKILL.md +239 -0
- package/rules/golang/ent-orm/references/REFERENCE.md +13 -0
- package/rules/golang/ent-orm/references/schema-patterns.md +255 -0
- package/rules/golang/fiber-framework/SKILL.md +196 -0
- package/rules/golang/fiber-framework/references/REFERENCE.md +13 -0
- package/rules/golang/fiber-framework/references/routing-patterns.md +191 -0
- package/rules/golang/gin-framework/SKILL.md +205 -0
- package/rules/golang/gin-framework/references/REFERENCE.md +14 -0
- package/rules/golang/gin-framework/references/middleware-patterns.md +119 -0
- package/rules/golang/gorm-orm/SKILL.md +196 -0
- package/rules/golang/gorm-orm/references/REFERENCE.md +14 -0
- package/rules/golang/gorm-orm/references/model-definitions.md +167 -0
- package/rules/golang/gorm-orm/references/query-patterns.md +161 -0
- package/rules/golang/grpc/SKILL.md +231 -0
- package/rules/golang/grpc/references/REFERENCE.md +13 -0
- package/rules/golang/grpc/references/service-patterns.md +276 -0
- package/rules/golang/testify/SKILL.md +239 -0
- package/rules/golang/testify/references/REFERENCE.md +13 -0
- package/rules/golang/testify/references/assert-patterns.md +170 -0
- package/rules/golang/validator/SKILL.md +234 -0
- package/rules/golang/validator/references/REFERENCE.md +13 -0
- package/rules/golang/validator/references/validation-tags.md +211 -0
- package/rules/golang/viper-config/SKILL.md +244 -0
- package/rules/golang/viper-config/references/REFERENCE.md +13 -0
- package/rules/golang/viper-config/references/config-loading.md +181 -0
- package/rules/golang/wire-di/SKILL.md +243 -0
- package/rules/golang/wire-di/references/REFERENCE.md +13 -0
- package/rules/golang/wire-di/references/provider-patterns.md +193 -0
- package/rules/golang/zap-logging/SKILL.md +203 -0
- package/rules/golang/zap-logging/references/REFERENCE.md +13 -0
- package/rules/golang/zap-logging/references/logger-config.md +165 -0
- package/rules/java/build-gradle/SKILL.md +92 -0
- package/rules/java/build-gradle/references/REFERENCE.md +14 -0
- package/rules/java/build-gradle/references/kotlin-dsl.md +118 -0
- package/rules/java/build-gradle/references/task-configuration.md +132 -0
- package/rules/java/build-maven/SKILL.md +86 -0
- package/rules/java/build-maven/references/REFERENCE.md +14 -0
- package/rules/java/build-maven/references/dependency-management.md +111 -0
- package/rules/java/build-maven/references/lifecycle-phases.md +114 -0
- package/rules/java/graalvm-native/SKILL.md +105 -0
- package/rules/java/graalvm-native/references/REFERENCE.md +12 -0
- package/rules/java/java-collections-streams/SKILL.md +148 -0
- package/rules/java/java-collections-streams/references/REFERENCE.md +15 -0
- package/rules/java/java-collections-streams/references/collectors-patterns.md +178 -0
- package/rules/java/java-collections-streams/references/stream-pipelines.md +165 -0
- package/rules/java/java-concurrency/SKILL.md +187 -0
- package/rules/java/java-concurrency/references/REFERENCE.md +17 -0
- package/rules/java/java-concurrency/references/completable-future.md +165 -0
- package/rules/java/java-concurrency/references/executor-patterns.md +176 -0
- package/rules/java/java-concurrency/references/virtual-threads.md +190 -0
- package/rules/java/java-core-language/SKILL.md +121 -0
- package/rules/java/java-core-language/references/REFERENCE.md +15 -0
- package/rules/java/java-core-language/references/jvm-memory-model.md +160 -0
- package/rules/java/java-core-language/references/modern-java-features.md +168 -0
- package/rules/java/java-project-structure/SKILL.md +195 -0
- package/rules/java/java-project-structure/references/REFERENCE.md +15 -0
- package/rules/java/java-project-structure/references/maven-project-layout.md +199 -0
- package/rules/java/java-project-structure/references/module-system.md +159 -0
- package/rules/java/micronaut-core/SKILL.md +99 -0
- package/rules/java/micronaut-core/references/REFERENCE.md +12 -0
- package/rules/java/micronaut-reactive/SKILL.md +68 -0
- package/rules/java/micronaut-reactive/references/REFERENCE.md +12 -0
- package/rules/java/quarkus-core/SKILL.md +85 -0
- package/rules/java/quarkus-core/references/REFERENCE.md +12 -0
- package/rules/java/quarkus-reactive/SKILL.md +67 -0
- package/rules/java/quarkus-reactive/references/REFERENCE.md +12 -0
- package/rules/java/spring-batch/SKILL.md +102 -0
- package/rules/java/spring-batch/references/REFERENCE.md +12 -0
- package/rules/java/spring-boot-architecture/SKILL.md +206 -0
- package/rules/java/spring-boot-architecture/references/REFERENCE.md +15 -0
- package/rules/java/spring-boot-architecture/references/auto-configuration.md +158 -0
- package/rules/java/spring-boot-architecture/references/configuration-properties.md +202 -0
- package/rules/java/spring-boot-web/SKILL.md +217 -0
- package/rules/java/spring-boot-web/references/REFERENCE.md +17 -0
- package/rules/java/spring-cloud/SKILL.md +109 -0
- package/rules/java/spring-cloud/references/REFERENCE.md +13 -0
- package/rules/java/spring-data-jpa/SKILL.md +241 -0
- package/rules/java/spring-data-jpa/references/REFERENCE.md +16 -0
- package/rules/java/spring-security/SKILL.md +161 -0
- package/rules/java/spring-security/references/REFERENCE.md +16 -0
- package/rules/java/spring-security/references/jwt-auth-flow.md +213 -0
- package/rules/java/testing-junit-mockito/SKILL.md +135 -0
- package/rules/java/testing-junit-mockito/references/REFERENCE.md +15 -0
- package/rules/java/testing-junit-mockito/references/junit5-patterns.md +159 -0
- package/rules/java/testing-junit-mockito/references/mockito-patterns.md +148 -0
- package/rules/java/testing-junit-mockito/references/spring-boot-testing.md +152 -0
- package/rules/javascript/best-practices/SKILL.md +64 -0
- package/rules/javascript/best-practices/references/REFERENCE.md +91 -0
- package/rules/javascript/language/SKILL.md +71 -0
- package/rules/javascript/language/references/REFERENCE.md +106 -0
- package/rules/javascript/tooling/SKILL.md +60 -0
- package/rules/javascript/tooling/references/REFERENCE.md +107 -0
- package/rules/metadata.json +54 -0
- package/rules/nestjs/api-standards/SKILL.md +47 -0
- package/rules/nestjs/api-standards/references/pagination-wrapper.md +87 -0
- package/rules/nestjs/architecture/SKILL.md +68 -0
- package/rules/nestjs/architecture/references/dynamic-module.md +53 -0
- package/rules/nestjs/caching/SKILL.md +51 -0
- package/rules/nestjs/caching/references/REFERENCE.md +13 -0
- package/rules/nestjs/caching/references/cache-patterns.md +183 -0
- package/rules/nestjs/configuration/SKILL.md +41 -0
- package/rules/nestjs/configuration/references/REFERENCE.md +13 -0
- package/rules/nestjs/configuration/references/config-patterns.md +184 -0
- package/rules/nestjs/controllers-services/SKILL.md +63 -0
- package/rules/nestjs/controllers-services/references/REFERENCE.md +14 -0
- package/rules/nestjs/controllers-services/references/controller-patterns.md +119 -0
- package/rules/nestjs/controllers-services/references/service-patterns.md +129 -0
- package/rules/nestjs/database/SKILL.md +102 -0
- package/rules/nestjs/database/references/REFERENCE.md +14 -0
- package/rules/nestjs/database/references/typeorm-patterns.md +156 -0
- package/rules/nestjs/deployment/SKILL.md +36 -0
- package/rules/nestjs/deployment/references/REFERENCE.md +13 -0
- package/rules/nestjs/deployment/references/deployment-patterns.md +140 -0
- package/rules/nestjs/documentation/SKILL.md +64 -0
- package/rules/nestjs/documentation/references/REFERENCE.md +13 -0
- package/rules/nestjs/documentation/references/swagger-patterns.md +139 -0
- package/rules/nestjs/error-handling/SKILL.md +55 -0
- package/rules/nestjs/error-handling/references/REFERENCE.md +13 -0
- package/rules/nestjs/error-handling/references/exception-filters.md +152 -0
- package/rules/nestjs/file-uploads/SKILL.md +35 -0
- package/rules/nestjs/file-uploads/references/REFERENCE.md +13 -0
- package/rules/nestjs/file-uploads/references/upload-patterns.md +125 -0
- package/rules/nestjs/observability/SKILL.md +39 -0
- package/rules/nestjs/observability/references/REFERENCE.md +13 -0
- package/rules/nestjs/observability/references/logging-metrics.md +175 -0
- package/rules/nestjs/performance/SKILL.md +60 -0
- package/rules/nestjs/performance/references/REFERENCE.md +13 -0
- package/rules/nestjs/performance/references/performance-patterns.md +107 -0
- package/rules/nestjs/real-time/SKILL.md +45 -0
- package/rules/nestjs/real-time/references/REFERENCE.md +13 -0
- package/rules/nestjs/real-time/references/websocket-patterns.md +121 -0
- package/rules/nestjs/scheduling/SKILL.md +39 -0
- package/rules/nestjs/scheduling/references/REFERENCE.md +13 -0
- package/rules/nestjs/scheduling/references/scheduling-patterns.md +137 -0
- package/rules/nestjs/search/SKILL.md +41 -0
- package/rules/nestjs/search/references/REFERENCE.md +13 -0
- package/rules/nestjs/search/references/search-patterns.md +137 -0
- package/rules/nestjs/security/SKILL.md +87 -0
- package/rules/nestjs/security/references/REFERENCE.md +14 -0
- package/rules/nestjs/security/references/authentication.md +151 -0
- package/rules/nestjs/testing/SKILL.md +40 -0
- package/rules/nestjs/testing/references/REFERENCE.md +14 -0
- package/rules/nestjs/testing/references/unit-testing.md +179 -0
- package/rules/nestjs/transport/SKILL.md +45 -0
- package/rules/nestjs/transport/references/REFERENCE.md +13 -0
- package/rules/nestjs/transport/references/microservices-patterns.md +170 -0
- package/rules/nextjs/app-router/SKILL.md +46 -0
- package/rules/nextjs/app-router/references/REFERENCE.md +14 -0
- package/rules/nextjs/app-router/references/routing-patterns.md +182 -0
- package/rules/nextjs/architecture/SKILL.md +44 -0
- package/rules/nextjs/architecture/references/fsd-structure.md +77 -0
- package/rules/nextjs/authentication/SKILL.md +29 -0
- package/rules/nextjs/authentication/references/auth-implementation.md +73 -0
- package/rules/nextjs/caching/SKILL.md +66 -0
- package/rules/nextjs/caching/references/REFERENCE.md +13 -0
- package/rules/nextjs/caching/references/cache-strategies.md +168 -0
- package/rules/nextjs/data-access-layer/SKILL.md +33 -0
- package/rules/nextjs/data-access-layer/references/patterns.md +66 -0
- package/rules/nextjs/data-fetching/SKILL.md +59 -0
- package/rules/nextjs/data-fetching/references/REFERENCE.md +13 -0
- package/rules/nextjs/data-fetching/references/fetch-patterns.md +160 -0
- package/rules/nextjs/internationalization/SKILL.md +105 -0
- package/rules/nextjs/internationalization/references/REFERENCE.md +13 -0
- package/rules/nextjs/internationalization/references/i18n-patterns.md +180 -0
- package/rules/nextjs/optimization/SKILL.md +64 -0
- package/rules/nextjs/optimization/references/REFERENCE.md +13 -0
- package/rules/nextjs/optimization/references/optimization-patterns.md +190 -0
- package/rules/nextjs/rendering/SKILL.md +91 -0
- package/rules/nextjs/rendering/references/REFERENCE.md +13 -0
- package/rules/nextjs/rendering/references/rendering-modes.md +163 -0
- package/rules/nextjs/server-actions/SKILL.md +46 -0
- package/rules/nextjs/server-actions/references/REFERENCE.md +13 -0
- package/rules/nextjs/server-actions/references/action-patterns.md +188 -0
- package/rules/nextjs/server-components/SKILL.md +52 -0
- package/rules/nextjs/server-components/references/REFERENCE.md +13 -0
- package/rules/nextjs/server-components/references/component-patterns.md +175 -0
- package/rules/nextjs/state-management/SKILL.md +73 -0
- package/rules/nextjs/state-management/references/REFERENCE.md +13 -0
- package/rules/nextjs/state-management/references/state-patterns.md +218 -0
- package/rules/nextjs/styling/SKILL.md +31 -0
- package/rules/nextjs/styling/references/implementation.md +56 -0
- package/rules/react/component-patterns/SKILL.md +66 -0
- package/rules/react/component-patterns/references/REFERENCE.md +126 -0
- package/rules/react/hooks/SKILL.md +60 -0
- package/rules/react/hooks/references/REFERENCE.md +132 -0
- package/rules/react/hooks.rule.md +79 -0
- package/rules/react/performance/SKILL.md +69 -0
- package/rules/react/performance/references/REFERENCE.md +143 -0
- package/rules/react/security/SKILL.md +46 -0
- package/rules/react/security/references/REFERENCE.md +170 -0
- package/rules/react/state-management/SKILL.md +56 -0
- package/rules/react/state-management/references/REFERENCE.md +137 -0
- package/rules/react/testing/SKILL.md +45 -0
- package/rules/react/testing/references/REFERENCE.md +149 -0
- package/rules/react/tooling/SKILL.md +39 -0
- package/rules/react/typescript/SKILL.md +53 -0
- package/rules/rust/actix-web/SKILL.md +160 -0
- package/rules/rust/actix-web/references/REFERENCE.md +13 -0
- package/rules/rust/actix-web/references/handler-patterns.md +198 -0
- package/rules/rust/async-graphql/SKILL.md +228 -0
- package/rules/rust/async-graphql/references/REFERENCE.md +13 -0
- package/rules/rust/async-graphql/references/schema-patterns.md +215 -0
- package/rules/rust/axum/SKILL.md +161 -0
- package/rules/rust/axum/references/REFERENCE.md +14 -0
- package/rules/rust/axum/references/handler-patterns.md +97 -0
- package/rules/rust/bevy/SKILL.md +206 -0
- package/rules/rust/bevy/references/REFERENCE.md +13 -0
- package/rules/rust/bevy/references/ecs-patterns.md +226 -0
- package/rules/rust/clap/SKILL.md +217 -0
- package/rules/rust/clap/references/REFERENCE.md +13 -0
- package/rules/rust/clap/references/derive-patterns.md +205 -0
- package/rules/rust/core/SKILL.md +154 -0
- package/rules/rust/core/references/REFERENCE.md +14 -0
- package/rules/rust/core/references/error-handling.md +92 -0
- package/rules/rust/diesel-orm/SKILL.md +176 -0
- package/rules/rust/diesel-orm/references/REFERENCE.md +13 -0
- package/rules/rust/diesel-orm/references/schema-patterns.md +206 -0
- package/rules/rust/rocket/SKILL.md +182 -0
- package/rules/rust/rocket/references/REFERENCE.md +13 -0
- package/rules/rust/rocket/references/handler-patterns.md +209 -0
- package/rules/rust/sea-orm/SKILL.md +230 -0
- package/rules/rust/sea-orm/references/REFERENCE.md +13 -0
- package/rules/rust/sea-orm/references/entity-patterns.md +221 -0
- package/rules/rust/serde-serialization/SKILL.md +150 -0
- package/rules/rust/serde-serialization/references/REFERENCE.md +13 -0
- package/rules/rust/serde-serialization/references/serialization-patterns.md +199 -0
- package/rules/rust/sqlx-database/SKILL.md +140 -0
- package/rules/rust/sqlx-database/references/REFERENCE.md +13 -0
- package/rules/rust/sqlx-database/references/query-patterns.md +210 -0
- package/rules/rust/tauri/SKILL.md +180 -0
- package/rules/rust/tauri/references/REFERENCE.md +13 -0
- package/rules/rust/tauri/references/command-patterns.md +209 -0
- package/rules/rust/tokio-runtime/SKILL.md +167 -0
- package/rules/rust/tokio-runtime/references/REFERENCE.md +14 -0
- package/rules/rust/tokio-runtime/references/async-patterns.md +137 -0
- package/rules/rust/tokio-runtime/references/synchronization.md +152 -0
- package/rules/rust/tonic/SKILL.md +231 -0
- package/rules/rust/tonic/references/REFERENCE.md +13 -0
- package/rules/rust/tonic/references/service-patterns.md +213 -0
- package/rules/rust/tracing/SKILL.md +214 -0
- package/rules/rust/tracing/references/REFERENCE.md +13 -0
- package/rules/rust/tracing/references/instrumentation.md +187 -0
- package/rules/typescript/best-practices/SKILL.md +108 -0
- package/rules/typescript/best-practices/references/REFERENCE.md +68 -0
- package/rules/typescript/language/SKILL.md +72 -0
- package/rules/typescript/language/references/REFERENCE.md +67 -0
- package/rules/typescript/patterns.rule.md +85 -0
- package/rules/typescript/security/SKILL.md +59 -0
- package/rules/typescript/security/references/REFERENCE.md +113 -0
- package/rules/typescript/tooling/SKILL.md +52 -0
- package/rules/typescript/tooling/references/REFERENCE.md +110 -0
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
# Virtual Threads (Java 21+)
|
|
2
|
+
|
|
3
|
+
## Overview
|
|
4
|
+
|
|
5
|
+
Virtual threads are lightweight threads managed by the JVM, not the OS. They enable the "thread-per-request" model without the overhead of platform threads.
|
|
6
|
+
|
|
7
|
+
## Basic Usage
|
|
8
|
+
|
|
9
|
+
```java
|
|
10
|
+
// Start a virtual thread
|
|
11
|
+
Thread.startVirtualThread(() -> {
|
|
12
|
+
// blocking I/O is fine - JVM will unmount from carrier thread
|
|
13
|
+
String response = httpClient.send(request, BodyHandlers.ofString()).body();
|
|
14
|
+
processResponse(response);
|
|
15
|
+
});
|
|
16
|
+
|
|
17
|
+
// Create named virtual thread
|
|
18
|
+
Thread vt = Thread.ofVirtual()
|
|
19
|
+
.name("my-virtual-thread")
|
|
20
|
+
.start(() -> doWork());
|
|
21
|
+
|
|
22
|
+
// Check if current thread is virtual
|
|
23
|
+
if (Thread.currentThread().isVirtual()) {
|
|
24
|
+
// running on virtual thread
|
|
25
|
+
}
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
## ExecutorService Pattern
|
|
29
|
+
|
|
30
|
+
```java
|
|
31
|
+
// Preferred: ExecutorService with virtual threads
|
|
32
|
+
try (var executor = Executors.newVirtualThreadPerTaskExecutor()) {
|
|
33
|
+
List<Future<Result>> futures = tasks.stream()
|
|
34
|
+
.map(task -> executor.submit(() -> processTask(task)))
|
|
35
|
+
.toList();
|
|
36
|
+
|
|
37
|
+
List<Result> results = new ArrayList<>();
|
|
38
|
+
for (Future<Result> future : futures) {
|
|
39
|
+
results.add(future.get()); // blocking is fine
|
|
40
|
+
}
|
|
41
|
+
return results;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
// For HTTP handlers (e.g., Tomcat, Jetty)
|
|
45
|
+
// Configure server to use virtual threads - each request gets its own
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
## Structured Concurrency (Preview)
|
|
49
|
+
|
|
50
|
+
```java
|
|
51
|
+
// Run subtasks with structured lifetime
|
|
52
|
+
try (var scope = new StructuredTaskScope.ShutdownOnFailure()) {
|
|
53
|
+
Subtask<User> userTask = scope.fork(() -> userService.find(userId));
|
|
54
|
+
Subtask<List<Order>> ordersTask = scope.fork(() -> orderService.findByUser(userId));
|
|
55
|
+
Subtask<Preferences> prefsTask = scope.fork(() -> prefsService.find(userId));
|
|
56
|
+
|
|
57
|
+
scope.join(); // Wait for all tasks
|
|
58
|
+
scope.throwIfFailed(); // Propagate exceptions
|
|
59
|
+
|
|
60
|
+
return new UserProfile(
|
|
61
|
+
userTask.get(),
|
|
62
|
+
ordersTask.get(),
|
|
63
|
+
prefsTask.get()
|
|
64
|
+
);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
// ShutdownOnSuccess - cancel remaining tasks when one succeeds
|
|
68
|
+
try (var scope = new StructuredTaskScope.ShutdownOnSuccess<String>()) {
|
|
69
|
+
scope.fork(() -> fetchFromPrimary());
|
|
70
|
+
scope.fork(() -> fetchFromBackup());
|
|
71
|
+
|
|
72
|
+
scope.join();
|
|
73
|
+
return scope.result(); // First successful result
|
|
74
|
+
}
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
## When to Use Virtual Threads
|
|
78
|
+
|
|
79
|
+
### Good Use Cases
|
|
80
|
+
|
|
81
|
+
```java
|
|
82
|
+
// ✅ I/O-bound operations
|
|
83
|
+
void processRequests(List<Request> requests) {
|
|
84
|
+
try (var executor = Executors.newVirtualThreadPerTaskExecutor()) {
|
|
85
|
+
requests.forEach(req ->
|
|
86
|
+
executor.submit(() -> {
|
|
87
|
+
String data = httpClient.get(req.url()); // Network I/O
|
|
88
|
+
String result = database.query(req.query()); // Database I/O
|
|
89
|
+
fileSystem.write(result); // File I/O
|
|
90
|
+
})
|
|
91
|
+
);
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
// ✅ HTTP servers handling many concurrent connections
|
|
96
|
+
// ✅ Database-heavy applications
|
|
97
|
+
// ✅ Microservices making downstream calls
|
|
98
|
+
```
|
|
99
|
+
|
|
100
|
+
### When NOT to Use
|
|
101
|
+
|
|
102
|
+
```java
|
|
103
|
+
// ❌ CPU-bound computation - use platform threads
|
|
104
|
+
// Virtual threads don't help with CPU-bound work
|
|
105
|
+
void cpuIntensive(List<Data> data) {
|
|
106
|
+
// Use fixed thread pool sized to CPU cores
|
|
107
|
+
ExecutorService cpuPool = Executors.newFixedThreadPool(
|
|
108
|
+
Runtime.getRuntime().availableProcessors()
|
|
109
|
+
);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
// ❌ Long synchronized blocks - use ReentrantLock instead
|
|
113
|
+
// synchronized pins the carrier thread
|
|
114
|
+
synchronized (lock) {
|
|
115
|
+
// Long blocking operation - BAD
|
|
116
|
+
Thread.sleep(1000);
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// GOOD: Use ReentrantLock
|
|
120
|
+
lock.lock();
|
|
121
|
+
try {
|
|
122
|
+
Thread.sleep(1000); // Virtual thread unmounts during sleep
|
|
123
|
+
} finally {
|
|
124
|
+
lock.unlock();
|
|
125
|
+
}
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
## Migration Tips
|
|
129
|
+
|
|
130
|
+
```java
|
|
131
|
+
// 1. Replace thread pools with virtual thread executor
|
|
132
|
+
// Before
|
|
133
|
+
ExecutorService executor = Executors.newFixedThreadPool(200);
|
|
134
|
+
|
|
135
|
+
// After (for I/O-bound work)
|
|
136
|
+
ExecutorService executor = Executors.newVirtualThreadPerTaskExecutor();
|
|
137
|
+
|
|
138
|
+
// 2. Replace synchronized with ReentrantLock for blocking operations
|
|
139
|
+
// Before
|
|
140
|
+
synchronized (lock) {
|
|
141
|
+
blockingCall();
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
// After
|
|
145
|
+
private final ReentrantLock lock = new ReentrantLock();
|
|
146
|
+
|
|
147
|
+
lock.lock();
|
|
148
|
+
try {
|
|
149
|
+
blockingCall();
|
|
150
|
+
} finally {
|
|
151
|
+
lock.unlock();
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
// 3. Don't pool virtual threads - create new ones freely
|
|
155
|
+
// Virtual threads are cheap (~1KB vs ~1MB for platform threads)
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
## Debugging
|
|
159
|
+
|
|
160
|
+
```java
|
|
161
|
+
// Thread dumps show virtual threads
|
|
162
|
+
// jcmd <pid> Thread.dump_to_file -format=json threads.json
|
|
163
|
+
|
|
164
|
+
// Configure carrier thread count
|
|
165
|
+
// -Djdk.virtualThreadScheduler.parallelism=<n>
|
|
166
|
+
// -Djdk.virtualThreadScheduler.maxPoolSize=<n>
|
|
167
|
+
|
|
168
|
+
// Detect pinned virtual threads
|
|
169
|
+
// -Djdk.tracePinnedThreads=full
|
|
170
|
+
```
|
|
171
|
+
|
|
172
|
+
## Pitfalls
|
|
173
|
+
|
|
174
|
+
```java
|
|
175
|
+
// 1. ThreadLocal can consume memory with many virtual threads
|
|
176
|
+
// Use ScopedValue (preview) instead
|
|
177
|
+
private static final ScopedValue<User> CURRENT_USER = ScopedValue.newInstance();
|
|
178
|
+
|
|
179
|
+
ScopedValue.where(CURRENT_USER, user).run(() -> {
|
|
180
|
+
processRequest();
|
|
181
|
+
});
|
|
182
|
+
|
|
183
|
+
// 2. Don't use thread-per-task executor with CompletableFuture
|
|
184
|
+
// Each stage gets a new virtual thread - may be wasteful
|
|
185
|
+
CompletableFuture.supplyAsync(task, virtualExecutor)
|
|
186
|
+
.thenApplyAsync(transform, virtualExecutor); // Unnecessary
|
|
187
|
+
|
|
188
|
+
// 3. Monitor carrier thread pinning
|
|
189
|
+
// Long synchronized blocks or native calls pin carrier threads
|
|
190
|
+
```
|
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: Java Core Language
|
|
3
|
+
description: Java language fundamentals, JVM basics, modern features, and idiomatic patterns.
|
|
4
|
+
metadata:
|
|
5
|
+
labels: [java, core, language]
|
|
6
|
+
triggers:
|
|
7
|
+
files: ['**/*.java', 'pom.xml', 'build.gradle', 'build.gradle.kts']
|
|
8
|
+
keywords: [class, interface, record, enum, package, import, extends, implements, throws, sealed, permits]
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
# Java Core Language Standards
|
|
12
|
+
|
|
13
|
+
## Modern Java Features (17+)
|
|
14
|
+
|
|
15
|
+
```java
|
|
16
|
+
// Records - immutable data carriers
|
|
17
|
+
public record User(String id, String name, String email) {
|
|
18
|
+
// Compact constructor for validation
|
|
19
|
+
public User {
|
|
20
|
+
Objects.requireNonNull(id);
|
|
21
|
+
Objects.requireNonNull(name);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
// Sealed classes - restricted inheritance
|
|
26
|
+
public sealed interface Shape permits Circle, Rectangle, Triangle {}
|
|
27
|
+
public record Circle(double radius) implements Shape {}
|
|
28
|
+
public record Rectangle(double width, double height) implements Shape {}
|
|
29
|
+
public final class Triangle implements Shape { /* ... */ }
|
|
30
|
+
|
|
31
|
+
// Pattern matching for switch (21+)
|
|
32
|
+
String describe(Shape shape) {
|
|
33
|
+
return switch (shape) {
|
|
34
|
+
case Circle(var r) -> "Circle with radius " + r;
|
|
35
|
+
case Rectangle(var w, var h) -> "Rectangle " + w + "x" + h;
|
|
36
|
+
case Triangle t -> "Triangle";
|
|
37
|
+
};
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
// Pattern matching for instanceof
|
|
41
|
+
if (obj instanceof String s && !s.isBlank()) {
|
|
42
|
+
return s.toUpperCase();
|
|
43
|
+
}
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
## Exception Handling
|
|
47
|
+
|
|
48
|
+
```java
|
|
49
|
+
// Custom exception hierarchy
|
|
50
|
+
public class DomainException extends RuntimeException {
|
|
51
|
+
private final ErrorCode code;
|
|
52
|
+
|
|
53
|
+
public DomainException(ErrorCode code, String message) {
|
|
54
|
+
super(message);
|
|
55
|
+
this.code = code;
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
public DomainException(ErrorCode code, String message, Throwable cause) {
|
|
59
|
+
super(message, cause);
|
|
60
|
+
this.code = code;
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
// Try-with-resources
|
|
65
|
+
try (var reader = new BufferedReader(new FileReader(path));
|
|
66
|
+
var writer = new BufferedWriter(new FileWriter(output))) {
|
|
67
|
+
reader.lines().map(String::toUpperCase).forEach(writer::write);
|
|
68
|
+
} catch (IOException e) {
|
|
69
|
+
throw new DomainException(ErrorCode.IO_ERROR, "File processing failed", e);
|
|
70
|
+
}
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
## Generics
|
|
74
|
+
|
|
75
|
+
```java
|
|
76
|
+
// Bounded type parameters
|
|
77
|
+
public <T extends Comparable<T>> T max(T a, T b) {
|
|
78
|
+
return a.compareTo(b) > 0 ? a : b;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// Wildcards
|
|
82
|
+
void processItems(List<? extends Number> items) { /* read-only */ }
|
|
83
|
+
void addItems(List<? super Integer> items) { /* write-only */ }
|
|
84
|
+
|
|
85
|
+
// Generic method with multiple bounds
|
|
86
|
+
public <T extends Serializable & Comparable<T>> void process(T item) {}
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
## Null Safety
|
|
90
|
+
|
|
91
|
+
```java
|
|
92
|
+
// Use Optional for return types
|
|
93
|
+
public Optional<User> findById(String id) {
|
|
94
|
+
return Optional.ofNullable(repository.get(id));
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
// Never use Optional as parameter or field
|
|
98
|
+
// Use @Nullable annotation for nullable parameters
|
|
99
|
+
public void process(@Nullable String input) {
|
|
100
|
+
if (input == null) return;
|
|
101
|
+
// ...
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
// Objects utility methods
|
|
105
|
+
Objects.requireNonNull(param, "param must not be null");
|
|
106
|
+
Objects.requireNonNullElse(value, defaultValue);
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
## Best Practices
|
|
110
|
+
|
|
111
|
+
1. **Prefer records** for data transfer objects and value objects
|
|
112
|
+
2. **Use sealed classes** when you have a fixed set of subtypes
|
|
113
|
+
3. **Pattern matching** over instanceof chains and visitor pattern
|
|
114
|
+
4. **Immutability by default** - use final fields, unmodifiable collections
|
|
115
|
+
5. **Fail fast** - validate at boundaries, throw early
|
|
116
|
+
6. **Meaningful exceptions** - include context, use exception chaining
|
|
117
|
+
|
|
118
|
+
## References
|
|
119
|
+
|
|
120
|
+
- [Modern Java Features](references/modern-java-features.md) - Records, Sealed Classes, Pattern Matching
|
|
121
|
+
- [JVM Memory Model](references/jvm-memory-model.md) - Memory, GC, Performance
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# Java Core Language References
|
|
2
|
+
|
|
3
|
+
## References
|
|
4
|
+
|
|
5
|
+
- [**Modern Java Features**](modern-java-features.md) - Records, Sealed Classes, Pattern Matching, Text Blocks
|
|
6
|
+
- [**JVM Memory Model**](jvm-memory-model.md) - Memory layout, Garbage Collection, Performance tuning
|
|
7
|
+
|
|
8
|
+
## Quick Checks
|
|
9
|
+
|
|
10
|
+
- [ ] Use records for DTOs and value objects
|
|
11
|
+
- [ ] Use sealed classes for closed type hierarchies
|
|
12
|
+
- [ ] Pattern matching over instanceof chains
|
|
13
|
+
- [ ] Try-with-resources for all AutoCloseable
|
|
14
|
+
- [ ] Objects.requireNonNull at method entry points
|
|
15
|
+
- [ ] Optional for return types only, never parameters or fields
|
|
@@ -0,0 +1,160 @@
|
|
|
1
|
+
# JVM Memory Model
|
|
2
|
+
|
|
3
|
+
## Memory Layout
|
|
4
|
+
|
|
5
|
+
```
|
|
6
|
+
+------------------+
|
|
7
|
+
| Method Area | <- Class metadata, static fields
|
|
8
|
+
+------------------+
|
|
9
|
+
| Heap | <- Objects, arrays
|
|
10
|
+
| +------------+ |
|
|
11
|
+
| | Young | | <- New objects (Eden + Survivor)
|
|
12
|
+
| +------------+ |
|
|
13
|
+
| | Old | | <- Long-lived objects
|
|
14
|
+
| +------------+ |
|
|
15
|
+
+------------------+
|
|
16
|
+
| Stack | <- Per-thread, local variables, method calls
|
|
17
|
+
+------------------+
|
|
18
|
+
| Native Stack | <- JNI calls
|
|
19
|
+
+------------------+
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
## Garbage Collection
|
|
23
|
+
|
|
24
|
+
### GC Algorithms
|
|
25
|
+
|
|
26
|
+
```java
|
|
27
|
+
// G1GC (default since Java 9) - balanced latency/throughput
|
|
28
|
+
// -XX:+UseG1GC
|
|
29
|
+
// Good for: heap > 4GB, pause time < 200ms
|
|
30
|
+
|
|
31
|
+
// ZGC (Java 15+) - ultra-low latency
|
|
32
|
+
// -XX:+UseZGC
|
|
33
|
+
// Good for: heap > 16GB, pause time < 10ms
|
|
34
|
+
|
|
35
|
+
// Shenandoah (Java 15+) - low latency, Red Hat
|
|
36
|
+
// -XX:+UseShenandoahGC
|
|
37
|
+
|
|
38
|
+
// Parallel GC - high throughput
|
|
39
|
+
// -XX:+UseParallelGC
|
|
40
|
+
// Good for: batch processing, throughput > latency
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
### GC Tuning Parameters
|
|
44
|
+
|
|
45
|
+
```bash
|
|
46
|
+
# Heap sizing
|
|
47
|
+
-Xms4g # Initial heap size
|
|
48
|
+
-Xmx4g # Maximum heap size
|
|
49
|
+
-XX:NewRatio=2 # Old/Young ratio (Old = 2x Young)
|
|
50
|
+
|
|
51
|
+
# G1GC tuning
|
|
52
|
+
-XX:MaxGCPauseMillis=200 # Target pause time
|
|
53
|
+
-XX:G1HeapRegionSize=8m # Region size (1-32MB)
|
|
54
|
+
-XX:InitiatingHeapOccupancyPercent=45
|
|
55
|
+
|
|
56
|
+
# ZGC tuning
|
|
57
|
+
-XX:ZAllocationSpikeTolerance=2
|
|
58
|
+
-XX:ZCollectionInterval=0 # Disable proactive GC
|
|
59
|
+
|
|
60
|
+
# Logging
|
|
61
|
+
-Xlog:gc*:file=gc.log:time,level,tags
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
## Memory Leak Prevention
|
|
65
|
+
|
|
66
|
+
```java
|
|
67
|
+
// 1. Close resources properly
|
|
68
|
+
try (Connection conn = dataSource.getConnection();
|
|
69
|
+
PreparedStatement stmt = conn.prepareStatement(sql)) {
|
|
70
|
+
// use resources
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
// 2. Remove listeners when done
|
|
74
|
+
public class MyComponent {
|
|
75
|
+
private final EventListener listener;
|
|
76
|
+
|
|
77
|
+
public void init() {
|
|
78
|
+
listener = event -> handle(event);
|
|
79
|
+
eventBus.register(listener);
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
public void destroy() {
|
|
83
|
+
eventBus.unregister(listener); // Important!
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
// 3. Use WeakReference for caches
|
|
88
|
+
Map<Key, WeakReference<Value>> cache = new WeakHashMap<>();
|
|
89
|
+
|
|
90
|
+
// 4. Avoid static collections holding object references
|
|
91
|
+
// BAD: static List<Object> cache = new ArrayList<>();
|
|
92
|
+
// GOOD: Use proper caching library with eviction
|
|
93
|
+
|
|
94
|
+
// 5. Be careful with inner classes
|
|
95
|
+
// Non-static inner class holds reference to outer class
|
|
96
|
+
class Outer {
|
|
97
|
+
// BAD: holds reference to Outer
|
|
98
|
+
class Inner {}
|
|
99
|
+
|
|
100
|
+
// GOOD: no reference to Outer
|
|
101
|
+
static class StaticInner {}
|
|
102
|
+
}
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
## Profiling Tools
|
|
106
|
+
|
|
107
|
+
```bash
|
|
108
|
+
# JFR (Java Flight Recorder)
|
|
109
|
+
java -XX:StartFlightRecording=duration=60s,filename=recording.jfr MyApp
|
|
110
|
+
|
|
111
|
+
# Heap dump
|
|
112
|
+
jmap -dump:format=b,file=heap.hprof <pid>
|
|
113
|
+
|
|
114
|
+
# Thread dump
|
|
115
|
+
jstack <pid> > threads.txt
|
|
116
|
+
|
|
117
|
+
# Native Memory Tracking
|
|
118
|
+
java -XX:NativeMemoryTracking=summary MyApp
|
|
119
|
+
jcmd <pid> VM.native_memory summary
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
## Performance Best Practices
|
|
123
|
+
|
|
124
|
+
```java
|
|
125
|
+
// 1. Avoid creating unnecessary objects
|
|
126
|
+
// BAD
|
|
127
|
+
for (int i = 0; i < 1000; i++) {
|
|
128
|
+
String s = new String("constant"); // Creates 1000 objects
|
|
129
|
+
}
|
|
130
|
+
// GOOD
|
|
131
|
+
String s = "constant"; // String pool, single object
|
|
132
|
+
|
|
133
|
+
// 2. Use StringBuilder for concatenation in loops
|
|
134
|
+
StringBuilder sb = new StringBuilder();
|
|
135
|
+
for (String item : items) {
|
|
136
|
+
sb.append(item).append(",");
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
// 3. Size collections appropriately
|
|
140
|
+
List<String> list = new ArrayList<>(expectedSize);
|
|
141
|
+
Map<K, V> map = new HashMap<>(expectedSize, 0.75f);
|
|
142
|
+
|
|
143
|
+
// 4. Use primitives over wrappers when possible
|
|
144
|
+
// BAD: Long sum = 0L;
|
|
145
|
+
// GOOD: long sum = 0L;
|
|
146
|
+
|
|
147
|
+
// 5. Lazy initialization for expensive objects
|
|
148
|
+
private volatile ExpensiveObject instance;
|
|
149
|
+
|
|
150
|
+
public ExpensiveObject getInstance() {
|
|
151
|
+
if (instance == null) {
|
|
152
|
+
synchronized (this) {
|
|
153
|
+
if (instance == null) {
|
|
154
|
+
instance = new ExpensiveObject();
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
return instance;
|
|
159
|
+
}
|
|
160
|
+
```
|
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
# Modern Java Features
|
|
2
|
+
|
|
3
|
+
## Records (Java 16+)
|
|
4
|
+
|
|
5
|
+
```java
|
|
6
|
+
// Basic record
|
|
7
|
+
public record Point(int x, int y) {}
|
|
8
|
+
|
|
9
|
+
// Record with validation
|
|
10
|
+
public record Email(String value) {
|
|
11
|
+
public Email {
|
|
12
|
+
if (!value.matches("^[\\w.-]+@[\\w.-]+\\.[a-z]{2,}$")) {
|
|
13
|
+
throw new IllegalArgumentException("Invalid email: " + value);
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
// Record with additional methods
|
|
19
|
+
public record Range(int start, int end) {
|
|
20
|
+
public Range {
|
|
21
|
+
if (start > end) throw new IllegalArgumentException("start > end");
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
public int length() {
|
|
25
|
+
return end - start;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
public boolean contains(int value) {
|
|
29
|
+
return value >= start && value <= end;
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
// Record implementing interface
|
|
34
|
+
public record ImmutableUser(String id, String name) implements Identifiable {
|
|
35
|
+
@Override
|
|
36
|
+
public String getId() {
|
|
37
|
+
return id;
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
## Sealed Classes (Java 17+)
|
|
43
|
+
|
|
44
|
+
```java
|
|
45
|
+
// Sealed interface with permits
|
|
46
|
+
public sealed interface Result<T> permits Success, Failure {
|
|
47
|
+
T getOrThrow();
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
public record Success<T>(T value) implements Result<T> {
|
|
51
|
+
@Override
|
|
52
|
+
public T getOrThrow() {
|
|
53
|
+
return value;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
public record Failure<T>(Exception error) implements Result<T> {
|
|
58
|
+
@Override
|
|
59
|
+
public T getOrThrow() {
|
|
60
|
+
throw new RuntimeException(error);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
// Usage with pattern matching
|
|
65
|
+
public <T> void handle(Result<T> result) {
|
|
66
|
+
switch (result) {
|
|
67
|
+
case Success<T>(var value) -> process(value);
|
|
68
|
+
case Failure<T>(var error) -> logError(error);
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
## Pattern Matching
|
|
74
|
+
|
|
75
|
+
```java
|
|
76
|
+
// Pattern matching for instanceof (Java 16+)
|
|
77
|
+
public String format(Object obj) {
|
|
78
|
+
if (obj instanceof String s) {
|
|
79
|
+
return "String: " + s;
|
|
80
|
+
} else if (obj instanceof Integer i) {
|
|
81
|
+
return "Integer: " + i;
|
|
82
|
+
} else if (obj instanceof List<?> list && !list.isEmpty()) {
|
|
83
|
+
return "Non-empty list of size: " + list.size();
|
|
84
|
+
}
|
|
85
|
+
return "Unknown: " + obj;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
// Pattern matching for switch (Java 21+)
|
|
89
|
+
public double area(Shape shape) {
|
|
90
|
+
return switch (shape) {
|
|
91
|
+
case Circle(var r) -> Math.PI * r * r;
|
|
92
|
+
case Rectangle(var w, var h) -> w * h;
|
|
93
|
+
case Triangle(var b, var h) -> 0.5 * b * h;
|
|
94
|
+
case null -> 0.0;
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
// Guarded patterns
|
|
99
|
+
public String classify(Integer i) {
|
|
100
|
+
return switch (i) {
|
|
101
|
+
case Integer n when n < 0 -> "negative";
|
|
102
|
+
case Integer n when n == 0 -> "zero";
|
|
103
|
+
case Integer n when n > 0 && n < 10 -> "small positive";
|
|
104
|
+
case Integer n -> "large positive";
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
## Text Blocks (Java 15+)
|
|
110
|
+
|
|
111
|
+
```java
|
|
112
|
+
// Multi-line strings
|
|
113
|
+
String json = """
|
|
114
|
+
{
|
|
115
|
+
"name": "%s",
|
|
116
|
+
"email": "%s",
|
|
117
|
+
"roles": ["user", "admin"]
|
|
118
|
+
}
|
|
119
|
+
""".formatted(name, email);
|
|
120
|
+
|
|
121
|
+
// SQL queries
|
|
122
|
+
String query = """
|
|
123
|
+
SELECT u.id, u.name, u.email
|
|
124
|
+
FROM users u
|
|
125
|
+
JOIN roles r ON u.role_id = r.id
|
|
126
|
+
WHERE r.name = :roleName
|
|
127
|
+
ORDER BY u.created_at DESC
|
|
128
|
+
""";
|
|
129
|
+
|
|
130
|
+
// HTML templates
|
|
131
|
+
String html = """
|
|
132
|
+
<html>
|
|
133
|
+
<body>
|
|
134
|
+
<h1>Welcome, %s</h1>
|
|
135
|
+
</body>
|
|
136
|
+
</html>
|
|
137
|
+
""".formatted(username);
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
## Virtual Threads (Java 21+)
|
|
141
|
+
|
|
142
|
+
```java
|
|
143
|
+
// Create virtual thread
|
|
144
|
+
Thread.startVirtualThread(() -> {
|
|
145
|
+
doBlockingOperation();
|
|
146
|
+
});
|
|
147
|
+
|
|
148
|
+
// Executor with virtual threads
|
|
149
|
+
try (var executor = Executors.newVirtualThreadPerTaskExecutor()) {
|
|
150
|
+
List<Future<String>> futures = urls.stream()
|
|
151
|
+
.map(url -> executor.submit(() -> fetchUrl(url)))
|
|
152
|
+
.toList();
|
|
153
|
+
|
|
154
|
+
for (Future<String> future : futures) {
|
|
155
|
+
System.out.println(future.get());
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
// Structured concurrency (preview)
|
|
160
|
+
try (var scope = new StructuredTaskScope.ShutdownOnFailure()) {
|
|
161
|
+
Subtask<User> user = scope.fork(() -> fetchUser(userId));
|
|
162
|
+
Subtask<List<Order>> orders = scope.fork(() -> fetchOrders(userId));
|
|
163
|
+
|
|
164
|
+
scope.join().throwIfFailed();
|
|
165
|
+
|
|
166
|
+
return new UserWithOrders(user.get(), orders.get());
|
|
167
|
+
}
|
|
168
|
+
```
|