Skip to content
Draft
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
17 commits
Select commit Hold shift + click to select a range
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Added examples for DataFrame Spring integration with CSV data sources…
… and improved build.gradle configuration.
  • Loading branch information
zaleslaw committed Sep 2, 2025
commit 26dbba8e38ea8a7c9f1b5457e966ab8638a9b11c
67 changes: 36 additions & 31 deletions build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -172,42 +172,47 @@ val modulesUsingJava17 = with(projects) {
}.map { it.path }

allprojects {
if (path in modulesUsingJava11) {
tasks.withType<KotlinCompile> {
compilerOptions {
jvmTarget = JvmTarget.JVM_11
freeCompilerArgs.add("-Xjdk-release=11")
when (path) {
in modulesUsingJava11 -> {
tasks.withType<KotlinCompile> {
compilerOptions {
jvmTarget = JvmTarget.JVM_11
freeCompilerArgs.add("-Xjdk-release=11")
}
}
}
tasks.withType<JavaCompile> {
sourceCompatibility = JavaVersion.VERSION_11.toString()
targetCompatibility = JavaVersion.VERSION_11.toString()
options.release.set(11)
}
}
else if (path in modulesUsingJava17) {
tasks.withType<KotlinCompile> {
compilerOptions {
jvmTarget = JvmTarget.JVM_17
freeCompilerArgs.add("-Xjdk-release=17")
tasks.withType<JavaCompile> {
sourceCompatibility = JavaVersion.VERSION_11.toString()
targetCompatibility = JavaVersion.VERSION_11.toString()
options.release.set(11)
}
}
tasks.withType<JavaCompile> {
sourceCompatibility = JavaVersion.VERSION_17.toString()
targetCompatibility = JavaVersion.VERSION_17.toString()
options.release.set(17)
}
} else {
tasks.withType<KotlinCompile> {
compilerOptions {
jvmTarget = JvmTarget.JVM_1_8
freeCompilerArgs.add("-Xjdk-release=8")

in modulesUsingJava17 -> {
tasks.withType<KotlinCompile> {
compilerOptions {
jvmTarget = JvmTarget.JVM_17
freeCompilerArgs.add("-Xjdk-release=17")
}
}
tasks.withType<JavaCompile> {
sourceCompatibility = JavaVersion.VERSION_17.toString()
targetCompatibility = JavaVersion.VERSION_17.toString()
options.release.set(17)
}
}
tasks.withType<JavaCompile> {
sourceCompatibility = JavaVersion.VERSION_1_8.toString()
targetCompatibility = JavaVersion.VERSION_1_8.toString()
options.release.set(8)

else -> {
tasks.withType<KotlinCompile> {
compilerOptions {
jvmTarget = JvmTarget.JVM_1_8
freeCompilerArgs.add("-Xjdk-release=8")
}
}
tasks.withType<JavaCompile> {
sourceCompatibility = JavaVersion.VERSION_1_8.toString()
targetCompatibility = JavaVersion.VERSION_1_8.toString()
options.release.set(8)
}
}
}
tasks.withType<KotlinCompile> {
Expand Down
31 changes: 31 additions & 0 deletions dataframe-spring/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,37 @@ dependencies {
testImplementation(libs.kotestAssertions)
}

// Define examples source set
val examples by sourceSets.creating {
kotlin.srcDir("examples/src")
resources.srcDir("examples/resources")
}

// Configure examples classpath
configurations {
named("examplesImplementation") {
extendsFrom(configurations.implementation.get())
}
named("examplesRuntimeOnly") {
extendsFrom(configurations.runtimeOnly.get())
}
}

// Add dependencies for examples
dependencies {
"examplesImplementation"(project(":dataframe-spring"))
"examplesImplementation"("org.springframework:spring-context:6.2.7")
"examplesImplementation"("org.springframework:spring-beans:6.2.7")
}

// Task for running examples
tasks.register<JavaExec>("runExamples") {
group = "Examples"
description = "Runs the DataFrame Spring examples"
classpath = examples.runtimeClasspath
mainClass.set("org.jetbrains.kotlinx.dataframe.spring.examples.ExampleRunnerKt")
}

tasks.test {
useJUnitPlatform()
}
74 changes: 74 additions & 0 deletions dataframe-spring/examples/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
# DataFrame Spring Examples

This directory contains examples demonstrating the usage of the DataFrame Spring integration.

## Overview

The examples show how to use the DataFrame Spring module to automatically load data from various sources into DataFrames using annotations.

## Examples

1. **CSV Data Source** - Demonstrates loading DataFrames from CSV files using the `@CsvDataSource` annotation
2. **CSV Data Source with Spring Context** - Shows how to use the `@CsvDataSource` annotation within a Spring application context

## Running Examples

To run all examples:

```bash
./gradlew :dataframe-spring:runExamples
```

## Example Descriptions

### CSV Data Source

This example demonstrates how to use the `DataFramePostProcessor` to process a bean with `@CsvDataSource` annotations outside of a Spring context.

Key features:
- Loading CSV data with default comma delimiter
- Loading CSV data with custom delimiter (semicolon)
- Accessing the loaded data through a typed DataFrame

### CSV Data Source with Spring Context

This example demonstrates how to use the `DataFramePostProcessor` within a Spring application context to process beans with `@CsvDataSource` annotations.

Key features:
- Registering the `DataFramePostProcessor` in a Spring context
- Automatically processing beans with `@CsvDataSource` annotations
- Retrieving processed beans from the Spring context

## Data Models

The examples use the following data models:

- `CustomerRow` - Represents customer data with id, name, email, and age
- `SalesRow` - Represents sales data with sale ID, customer ID, amount, and date

## File Structure

```
examples/
├── src/ # Source code for examples
│ └── org/jetbrains/kotlinx/dataframe/spring/examples/
│ ├── CsvDataSourceExample.kt # Basic CSV example
│ ├── CsvDataSourceWithContextExample.kt # Spring context example
│ ├── DataModels.kt # Data models and utilities
│ └── ExampleRunner.kt # Main entry point
└── resources/ # Resource files for examples
└── data/ # Data files
├── customers.csv # Customer data (created at runtime)
└── sales.csv # Sales data (created at runtime)
```

## Learning Path

1. Start with the basic CSV example to understand how the `@CsvDataSource` annotation works
2. Move on to the Spring context example to see how to integrate with Spring

## Additional Resources

For more information, see:
- [DataFrame Spring README](../README.md)
- [DataFrame Spring Integration Guide](../INTEGRATION_GUIDE.md)
3 changes: 3 additions & 0 deletions dataframe-spring/examples/resources/data/README.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
This directory contains data files used by the DataFrame Spring examples.

The CSV files (customers.csv and sales.csv) are created dynamically when the examples are run.
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
package org.jetbrains.kotlinx.dataframe.spring.examples

import org.jetbrains.kotlinx.dataframe.spring.DataFramePostProcessor

/**
* Example demonstrating basic CSV data source processing.
*
* This example shows how to use the DataFramePostProcessor to process
* a bean with @CsvDataSource annotations outside of a Spring context.
*/
fun csvDataSourceExample() {
// Create sample CSV files in the resources directory
val resourcesDir = System.getProperty("user.dir") + "\\dataframe-spring\\examples\\resources"
createSampleData(resourcesDir)

try {
println("1. Creating DataFramePostProcessor...")
val processor = DataFramePostProcessor()

println("2. Processing @CsvDataSource annotations...")
val service = ExampleDataService()
processor.postProcessBeforeInitialization(service, "exampleService")

println("3. DataFrame loaded successfully!")
println(" - Rows loaded: ${service.customerData.rowsCount()}")
println(" - Columns: ${service.customerData.columnNames()}")

println("4. Running business logic...")
service.printCustomerCount()
service.printSalesCount()

println("✓ @CsvDataSource annotation processing completed successfully!")

} catch (e: Exception) {
println("✗ Error processing @DataSource annotations: ${e.message}")
e.printStackTrace()
} finally {
// Clean up sample files
cleanupSampleData(resourcesDir)
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
package org.jetbrains.kotlinx.dataframe.spring.examples

import org.jetbrains.kotlinx.dataframe.spring.DataFramePostProcessor
import org.springframework.context.annotation.AnnotationConfigApplicationContext

/**
* Example demonstrating CSV data source processing with Spring context.
*
* This example shows how to use the DataFramePostProcessor within a Spring
* application context to process beans with @CsvDataSource annotations.
*/
fun csvDataSourceWithContextExample() {
// Create sample CSV files in the resources directory
val resourcesDir = System.getProperty("user.dir") + "\\dataframe-spring\\examples\\resources"
createSampleData(resourcesDir)

try {
println("1. Bootstrapping Spring context...")
val ctx = AnnotationConfigApplicationContext().apply {
register(DataFramePostProcessor::class.java)
register(ExampleDataService::class.java)
refresh()
}

println("2. Getting ExampleDataService bean from context...")
val dataService = ctx.getBean(ExampleDataService::class.java)

println("3. DataFrame loaded successfully!")
println(" - Rows loaded: ${dataService.customerData.rowsCount()}")
println(" - Columns: ${dataService.customerData.columnNames()}")

println("4. Running business logic...")
dataService.printCustomerCount()
dataService.printSalesCount()

println("✓ @CsvDataSource annotation processing with Spring context completed successfully!")

} catch (e: Exception) {
println("✗ Error processing @DataSource annotations: ${e.message}")
e.printStackTrace()
} finally {
// Clean up sample files
cleanupSampleData(resourcesDir)
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
package org.jetbrains.kotlinx.dataframe.spring.examples

import org.jetbrains.kotlinx.dataframe.DataFrame
import org.jetbrains.kotlinx.dataframe.annotations.DataSchema
import org.jetbrains.kotlinx.dataframe.spring.annotations.CsvDataSource
import java.io.File

/**
* Data schema for customer records.
*
* This interface defines the structure of customer data loaded from CSV files.
*/
@DataSchema
interface CustomerRow {
val id: Int
val name: String
val email: String
val age: Int
}

/**
* Data schema for sales records.
*
* This interface defines the structure of sales data loaded from CSV files.
*/
@DataSchema
interface SalesRow {
val saleId: Int
val customerId: Int
val amount: Double
val date: String
}

/**
* Example service class that uses DataFrame annotations.
*
* This class demonstrates how to use the @CsvDataSource annotation
* to automatically load data from CSV files into DataFrames.
*/
class ExampleDataService {
@CsvDataSource(file = CUSTOMERS_CSV)
lateinit var customerData: DataFrame<CustomerRow>

@CsvDataSource(file = SALES_CSV, delimiter = ';')
lateinit var salesData: DataFrame<SalesRow>

/**
* Prints the total number of customers.
*/
fun printCustomerCount() {
println("Number of customers: ${customerData.rowsCount()}")
}

/**
* Prints the total number of sales.
*/
fun printSalesCount() {
println("Number of sales: ${salesData.rowsCount()}")
}
}

// Constants for file paths
const val CUSTOMERS_CSV = "data\\customers.csv"
const val SALES_CSV = "data\\sales.csv"

/**
* Creates sample CSV data files for the examples.
*
* This function creates customer and sales data files in the specified directory.
*
* @param directory The directory where the files will be created
*/
fun createSampleData(directory: String) {
// Create customer data
File("$directory\\$CUSTOMERS_CSV").apply {
parentFile.mkdirs()
writeText("""
id,name,email,age
1,John Doe,[email protected],28
2,Jane Smith,[email protected],32
3,Bob Johnson,[email protected],25
4,Alice Brown,[email protected],30
""".trimIndent())
}

// Create sales data with semicolon delimiter
File("$directory\\$SALES_CSV").apply {
parentFile.mkdirs()
writeText("""
sale_id;customer_id;amount;date
1;1;150.00;2023-01-15
2;2;200.50;2023-01-16
3;1;75.25;2023-01-17
4;3;300.00;2023-01-18
""".trimIndent())
}
}

/**
* Cleans up the sample data files.
*
* @param directory The directory where the files were created
*/
fun cleanupSampleData(directory: String) {
File("$directory\\$CUSTOMERS_CSV").delete()
File("$directory\\$SALES_CSV").delete()
}
Loading