refactor(page): 删除旧版页面文件
This commit is contained in:
@@ -0,0 +1,248 @@
|
||||
# Jackson Conversion Guide
|
||||
|
||||
## When This Applies
|
||||
|
||||
Detected when imports match `com.fasterxml.jackson.*`.
|
||||
|
||||
## Key Rules
|
||||
|
||||
1. **Annotation site targets**:
|
||||
- `@JsonProperty` on a Java field → `@field:JsonProperty` in Kotlin.
|
||||
- `@JsonProperty` on a Java getter → `@get:JsonProperty` in Kotlin.
|
||||
- When converting to Kotlin properties, apply BOTH `@field:` and `@get:` targets to
|
||||
match Java's dual annotation on field + getter.
|
||||
|
||||
2. **@JsonCreator**: Java's `@JsonCreator` static factory or constructor → Kotlin primary
|
||||
constructor. The `@JsonCreator` annotation is often unnecessary on Kotlin's primary
|
||||
constructor if using the Jackson Kotlin module, but preserve it for safety.
|
||||
|
||||
3. **@JsonIgnore**: Preserve exactly. Use `@get:JsonIgnore` or `@field:JsonIgnore`
|
||||
depending on original target.
|
||||
|
||||
4. **@JsonDeserialize / @JsonSerialize**: Preserve exactly with correct site targets.
|
||||
|
||||
5. **@JsonInclude**: Preserve on class or property level.
|
||||
|
||||
6. **@JsonFormat**: Preserve with `@field:JsonFormat` site target.
|
||||
|
||||
7. **Jackson Kotlin Module**: Note that projects using Jackson with Kotlin should add
|
||||
`jackson-module-kotlin` for proper Kotlin support (data classes, default values,
|
||||
nullable types). This is NOT something to add during conversion — just note it if
|
||||
missing.
|
||||
|
||||
8. **Builder pattern with @JsonPOJOBuilder**: Replace with primary constructor +
|
||||
`@JsonCreator` if converting to data class. Otherwise preserve.
|
||||
|
||||
---
|
||||
|
||||
## Example 1: DTO with Various Jackson Annotations
|
||||
|
||||
### Java Input
|
||||
|
||||
```java
|
||||
package com.acme.dto;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonIgnore;
|
||||
import com.fasterxml.jackson.annotation.JsonInclude;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
import com.fasterxml.jackson.annotation.JsonFormat;
|
||||
|
||||
/**
|
||||
* Data transfer object for an order summary.
|
||||
*/
|
||||
@JsonInclude(JsonInclude.Include.NON_NULL)
|
||||
public class OrderSummaryDto {
|
||||
|
||||
@JsonProperty("order_id")
|
||||
private final String orderId;
|
||||
|
||||
@JsonProperty("total_amount")
|
||||
private final double totalAmount;
|
||||
|
||||
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd")
|
||||
private final String createdDate;
|
||||
|
||||
@JsonIgnore
|
||||
private String internalNote;
|
||||
|
||||
public OrderSummaryDto(String orderId, double totalAmount, String createdDate) {
|
||||
this.orderId = orderId;
|
||||
this.totalAmount = totalAmount;
|
||||
this.createdDate = createdDate;
|
||||
}
|
||||
|
||||
@JsonProperty("order_id")
|
||||
public String getOrderId() {
|
||||
return orderId;
|
||||
}
|
||||
|
||||
@JsonProperty("total_amount")
|
||||
public double getTotalAmount() {
|
||||
return totalAmount;
|
||||
}
|
||||
|
||||
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd")
|
||||
public String getCreatedDate() {
|
||||
return createdDate;
|
||||
}
|
||||
|
||||
@JsonIgnore
|
||||
public String getInternalNote() {
|
||||
return internalNote;
|
||||
}
|
||||
|
||||
public void setInternalNote(String internalNote) {
|
||||
this.internalNote = internalNote;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Kotlin Output
|
||||
|
||||
```kotlin
|
||||
package com.acme.dto
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonIgnore
|
||||
import com.fasterxml.jackson.annotation.JsonInclude
|
||||
import com.fasterxml.jackson.annotation.JsonProperty
|
||||
import com.fasterxml.jackson.annotation.JsonFormat
|
||||
|
||||
/**
|
||||
* Data transfer object for an order summary.
|
||||
*
|
||||
* @property orderId unique identifier for the order, serialized as `"order_id"`
|
||||
* @property totalAmount total monetary amount, serialized as `"total_amount"`
|
||||
* @property createdDate date the order was created, formatted as `yyyy-MM-dd`
|
||||
*/
|
||||
@JsonInclude(JsonInclude.Include.NON_NULL)
|
||||
open class OrderSummaryDto(
|
||||
@field:JsonProperty("order_id")
|
||||
@get:JsonProperty("order_id")
|
||||
val orderId: String?,
|
||||
|
||||
@field:JsonProperty("total_amount")
|
||||
@get:JsonProperty("total_amount")
|
||||
val totalAmount: Double,
|
||||
|
||||
@field:JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd")
|
||||
@get:JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd")
|
||||
val createdDate: String?
|
||||
) {
|
||||
@field:JsonIgnore
|
||||
@get:JsonIgnore
|
||||
var internalNote: String? = null
|
||||
}
|
||||
```
|
||||
|
||||
**Key points:**
|
||||
- `@JsonInclude` stays at class level — no site target needed.
|
||||
- `@JsonProperty` gets both `@field:` and `@get:` to match the Java field + getter
|
||||
annotations.
|
||||
- `@JsonFormat` also gets both `@field:` and `@get:` since Java had it on both.
|
||||
- `@JsonIgnore` gets both `@field:` and `@get:` to suppress serialization fully.
|
||||
|
||||
---
|
||||
|
||||
## Example 2: Class with @JsonCreator Factory Method
|
||||
|
||||
### Java Input
|
||||
|
||||
```java
|
||||
package com.acme.model;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonCreator;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
/**
|
||||
* Immutable configuration entry deserialized from JSON.
|
||||
*/
|
||||
public class ConfigEntry {
|
||||
|
||||
private final String key;
|
||||
private final String value;
|
||||
private final boolean enabled;
|
||||
|
||||
@JsonCreator
|
||||
public static ConfigEntry create(
|
||||
@JsonProperty("key") String key,
|
||||
@JsonProperty("value") String value,
|
||||
@JsonProperty("enabled") boolean enabled) {
|
||||
return new ConfigEntry(key, value, enabled);
|
||||
}
|
||||
|
||||
private ConfigEntry(String key, String value, boolean enabled) {
|
||||
this.key = key;
|
||||
this.value = value;
|
||||
this.enabled = enabled;
|
||||
}
|
||||
|
||||
@JsonProperty("key")
|
||||
public String getKey() {
|
||||
return key;
|
||||
}
|
||||
|
||||
@JsonProperty("value")
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
|
||||
@JsonProperty("enabled")
|
||||
public boolean isEnabled() {
|
||||
return enabled;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Kotlin Output
|
||||
|
||||
```kotlin
|
||||
package com.acme.model
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonCreator
|
||||
import com.fasterxml.jackson.annotation.JsonProperty
|
||||
|
||||
/**
|
||||
* Immutable configuration entry deserialized from JSON.
|
||||
*
|
||||
* @property key the configuration key
|
||||
* @property value the configuration value
|
||||
* @property enabled whether this entry is active
|
||||
*/
|
||||
data class ConfigEntry @JsonCreator constructor(
|
||||
@field:JsonProperty("key")
|
||||
@get:JsonProperty("key")
|
||||
val key: String?,
|
||||
|
||||
@field:JsonProperty("value")
|
||||
@get:JsonProperty("value")
|
||||
val value: String?,
|
||||
|
||||
@field:JsonProperty("enabled")
|
||||
@get:JsonProperty("enabled")
|
||||
val enabled: Boolean
|
||||
) {
|
||||
companion object {
|
||||
/**
|
||||
* Factory method preserved for documentation; the primary constructor
|
||||
* with [JsonCreator] handles deserialization directly.
|
||||
*/
|
||||
@JsonCreator
|
||||
@JvmStatic
|
||||
fun create(
|
||||
@JsonProperty("key") key: String?,
|
||||
@JsonProperty("value") value: String?,
|
||||
@JsonProperty("enabled") enabled: Boolean
|
||||
): ConfigEntry = ConfigEntry(key, value, enabled)
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Key points:**
|
||||
- The Java `@JsonCreator` static factory is converted to a Kotlin primary constructor
|
||||
with `@JsonCreator`. The companion object factory is preserved for backward
|
||||
compatibility but the primary constructor handles deserialization.
|
||||
- The class becomes a `data class` since it is immutable and value-oriented.
|
||||
- `@JsonCreator` is kept on the primary constructor for safety, ensuring Jackson can
|
||||
deserialize even without the Jackson Kotlin module.
|
||||
- String parameters remain nullable (`String?`) since Java strings are nullable by
|
||||
default and there is no `@NonNull` or `Objects.requireNonNull` evidence.
|
||||
Reference in New Issue
Block a user