Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
13 changes: 11 additions & 2 deletions .github/workflows/codeql.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,17 @@ jobs:
security-events: write
steps:
- uses: actions/checkout@v5
- uses: actions/setup-java@v4
with:
distribution: 'temurin'
java-version: '17'
cache: 'gradle'
- uses: github/codeql-action/init@v3
with:
languages: 'java-kotlin'
- uses: github/codeql-action/autobuild@v3
# Custom build steps for Kotlin Multiplatform (avoid Android/iOS toolchains)
- name: Build Kotlin common metadata
run: ./gradlew :pollingengine:compileKotlinMetadata --no-daemon --stacktrace
- uses: github/codeql-action/analyze@v3

analyze-swift:
Expand All @@ -36,5 +43,7 @@ jobs:
- uses: github/codeql-action/init@v3
with:
languages: 'swift'
- uses: github/codeql-action/autobuild@v3
# Custom build steps for Swift (explicit xcodebuild)
- name: Build iOS app for simulator (no code signing)
run: xcodebuild -project iosApp/iosApp.xcodeproj -scheme iosApp -sdk iphonesimulator -configuration Release CODE_SIGNING_ALLOWED=NO build
- uses: github/codeql-action/analyze@v3
89 changes: 74 additions & 15 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
# PollingEngine

[![Maven Central](https://img.shields.io/maven-central/v/io.github.bosankus/pollingengine.svg?label=Maven%20Central)](https://central.sonatype.com/artifact/io.github.bosankus/pollingengine)
Last updated: 2025-09-08 17:36

[![Maven Central](https://img.shields.io/maven-central/v/in.androidplay/pollingengine.svg?label=Maven%20Central)](https://central.sonatype.com/artifact/in.androidplay/pollingengine)
![Kotlin](https://img.shields.io/badge/Kotlin-2.2.10-blue?logo=kotlin)
[![License: Apache-2.0](https://img.shields.io/badge/License-Apache--2.0-green.svg)](#license)
[![CI](https://img.shields.io/badge/CI-GitHub%20Actions-inactive.svg)](#setupbuild-instructions)
Expand All @@ -12,7 +14,6 @@ with:
- Timeouts (overall and per‑attempt)
- Cancellation and control APIs
- Observability hooks (attempt/result/complete)
- Pluggable logging and metrics

Mermaid flow diagram (GitHub renders this):

Expand All @@ -37,6 +38,9 @@ flowchart TD

## Project Overview

Note: Public API rename — PollingEngineApi has been renamed to PollingApi, and apps should use the
facade object `Polling` instead of referencing `PollingEngine` directly.

PollingEngine helps you repeatedly call a function until a condition is met or limits are reached.
It is designed for long‑polling workflows like waiting for a server job to complete, checking
payment status, etc.
Expand All @@ -47,39 +51,39 @@ Highlights:

- Simple DSL with pollingConfig { … }
- Backoff presets (e.g., BackoffPolicies.quick20s)
- Control operations: pause(id), resume(id), cancel(handle/id), cancelAll(), shutdown()
- Control operations: pause(id), resume(id), cancel(id), cancelAll(), shutdown()
- Domain‑level results via PollingResult and terminal PollingOutcome

## Installation and Dependency

Coordinates on Maven Central:

- groupId: io.github.bosankus
- groupId: in.androidplay
- artifactId: pollingengine
- version: 0.1.0
- version: 0.1.1

Gradle Kotlin DSL (Android/shared):

```kotlin
repositories { mavenCentral() }
dependencies { implementation("io.github.bosankus:pollingengine:0.1.0") }
dependencies { implementation("in.androidplay:pollingengine:0.1.1") }
```

Gradle Groovy DSL:

```groovy
repositories { mavenCentral() }
dependencies { implementation "io.github.bosankus:pollingengine:0.1.0" }
dependencies { implementation "in.androidplay:pollingengine:0.1.1" }
```

Maven:

```xml

<dependency>
<groupId>io.github.bosankus</groupId>
<groupId>in.androidplay</groupId>
<artifactId>pollingengine</artifactId>
<version>0.1.0</version>
<version>0.1.1</version>
</dependency>
```

Expand Down Expand Up @@ -112,17 +116,16 @@ cd iosApp && pod install
Basic shared usage:

```kotlin
import `in`.androidplay.pollingengine.models.PollingResult
import `in`.androidplay.pollingengine.polling.*

val config = pollingConfig<String> {
fetch { /* return PollingResult<String> */ TODO() }
success { it == "READY" }
retry(DefaultRetryPredicates.retryOnNetworkServerTimeout)
// Retry for common transient errors (network/server/timeout/unknown)
retry(RetryPredicates.networkOrServerOrTimeout)
backoff(BackoffPolicies.quick20s)
}

suspend fun run(): PollingOutcome<String> = PollingEngine.pollUntil(config)
suspend fun run(): PollingOutcome<String> = Polling.run(config)
```

Android example (ViewModel + Compose):
Expand All @@ -139,7 +142,7 @@ class StatusViewModel : ViewModel() {
}

fun runOnce() = viewModelScope.launch {
_status.value = PollingEngine.pollUntil(config).toString()
_status.value = Polling.run(config).toString()
}
}
```
Expand Down Expand Up @@ -212,7 +215,7 @@ Publishing to Maven Central uses com.vanniktech.maven.publish.
- Required environment variables/Gradle properties (typically set in CI):
- OSSRH_USERNAME, OSSRH_PASSWORD
- SIGNING_KEY (Base64 GPG private key), SIGNING_PASSWORD
- GROUP: io.github.bosankus (already configured)
- GROUP: in.androidplay (already configured)
- Commands:

```bash
Expand Down Expand Up @@ -255,3 +258,59 @@ Copyright (c) 2025 AndroidPlay
- Maintainer: @bosankus
- Issues: use [GitHub Issues](https://github.com/bosankus/PollingEngine/issues)
- Security: see [SECURITY.md](SECURITY.md)

## Control APIs and Runtime Updates

Start polling by collecting the returned Flow, and control active sessions by ID:

```kotlin
// Start and collect in your scope
val flow = Polling.startPolling(config)
val job = flow.onEach { outcome ->
println("Outcome: $outcome")
}.launchIn(scope)

// Introspection
val ids = Polling.listActiveIds() // suspend; returns List<String>
println("Active: $ids (count=${Polling.activePollsCount()})")

// Pause/resume first active session (example)
if (ids.isNotEmpty()) {
val id = ids.first()
Polling.pause(id)
// ... later
Polling.resume(id)

// Update backoff at runtime
Polling.updateBackoff(id, BackoffPolicies.quick20s)

// Cancel
Polling.cancel(id)
}

// Or cancel all
Polling.cancelAll()

// Stop collecting if needed
job.cancel()
```

## RetryPredicates examples

Built-ins to reduce boilerplate:

```kotlin
// Retry for network/server/timeout/unknown errors (recommended)
retry(RetryPredicates.networkOrServerOrTimeout)

// Always retry on failures
retry(RetryPredicates.always)

// Never retry on failures
retry(RetryPredicates.never)
```

## More documentation

- docs/pollingengine.md — Web Guide (overview, install, Android/iOS usage)
- docs/DeveloperGuide.md — Developer Guide (API overview, DSL, migration, reference)
6 changes: 3 additions & 3 deletions composeApp/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ kotlin {
jvmTarget.set(JvmTarget.JVM_11)
}
}

listOf(
iosArm64(),
iosSimulatorArm64()
Expand All @@ -23,15 +23,14 @@ kotlin {
isStatic = true
}
}

sourceSets {
androidMain.dependencies {
implementation(compose.preview)
implementation(libs.androidx.activity.compose)
}
commonMain.dependencies {
implementation(project(":pollingengine"))
//implementation(libs.pollingengine)
implementation(compose.runtime)
implementation(compose.foundation)
implementation(compose.material3)
Expand All @@ -41,6 +40,7 @@ kotlin {
implementation(libs.androidx.lifecycle.viewmodelCompose)
implementation(libs.androidx.lifecycle.runtimeCompose)
implementation(libs.kotlinx.coroutines.core)
implementation(libs.atomicfu)
}
commonTest.dependencies {
implementation(libs.kotlin.test)
Expand Down
Loading
Loading