You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

IntelliJ中客户端项目访问Akka Actor的依赖配置与结构问题

Great question! When building a client to talk to your Akka Actor server while reusing those message classes, the critical move is to split your shared code into a common module—this way both server and client can pull in the same definitions without duplication. Let’s walk through how to structure this and set up dependencies properly:

1. Project Structure Planning

The goal is to separate concerns so shared code lives in its own module, while server and client handle their specific logic. Here’s a clean, scalable structure:

your-root-project/
├── build.sbt
├── core/
│   ├── src/
│   │   └── main/
│   │       └── scala/
│   │           └── com/yourcompany/
│   │               └── messages/
│   │                   ├── Greet.scala
│   │                   ├── GreetResponse.scala
│   │                   └── SharedSerializers.scala
│   └── build.sbt
├── akka-server/
│   ├── src/
│   │   └── main/
│   │       ├── scala/
│   │       │   └── com/yourcompany/
│   │       │       ├── actors/
│   │       │       │   └── GreeterActor.scala
│   │       │       └── ServerApp.scala
│   │       └── resources/
│   │           └── application.conf
│   └── build.sbt
└── akka-client/
    ├── src/
    │   └── main/
    │       ├── scala/
    │       │   └── com/yourcompany/
    │       │       └── ClientApp.scala
    │       └── resources/
    │           └── application.conf
    └── build.sbt
  • Core Module: This holds all shared code—your message case classes, serialization helpers, and any common constants. Keep it lightweight, no unnecessary Akka dependencies beyond what’s needed for serialization.
  • Akka Server Module: Your existing Actor project, now depending on the core module. It contains your Actor implementations, server startup logic, and business rules.
  • Akka Client Module: A standalone project that pulls in the core module and Akka Remote (or Akka HTTP if you prefer REST) to send messages to the server.
2. Setting Up Dependencies

Core Module (core/build.sbt)

You’ll need Akka serialization utilities here since messages need to be serialized for network transport:

name := "core"
version := "1.0.0"
scalaVersion := "2.13.12" // Match your project's Scala version

libraryDependencies ++= Seq(
  "com.typesafe.akka" %% "akka-actor-typed" % "2.8.5", // Use untyped akka-actor if you're not using typed Actors
  "com.typesafe.akka" %% "akka-serialization-jackson" % "2.8.5" // Jackson for JSON serialization (Protobuf is another great option)
)

Akka Server Module (akka-server/build.sbt)

Depend on the core module and add Akka Remote for network communication:

name := "akka-server"
version := "1.0.0"
scalaVersion := "2.13.12"

// Reference the core module
lazy val core = project.in(file("../core"))

libraryDependencies ++= Seq(
  "com.typesafe.akka" %% "akka-actor-typed" % "2.8.5",
  "com.typesafe.akka" %% "akka-remote" % "2.8.5",
  "com.typesafe.akka" %% "akka-serialization-jackson" % "2.8.5"
)

// Pull in the core module's code
dependsOn(core)

Akka Client Module (akka-client/build.sbt)

Same logic as the server—depend on core and add Akka Remote:

name := "akka-client"
version := "1.0.0"
scalaVersion := "2.13.12"

lazy val core = project.in(file("../core"))

libraryDependencies ++= Seq(
  "com.typesafe.akka" %% "akka-actor-typed" % "2.8.5",
  "com.typesafe.akka" %% "akka-remote" % "2.8.5",
  "com.typesafe.akka" %% "akka-serialization-jackson" % "2.8.5"
)

dependsOn(core)
3. Key Communication Details
  • Serialization Setup: Ensure your message case classes are properly configured for serialization. For Jackson, Akka handles most case classes automatically, but you can add annotations if needed. For example:
    package com.yourcompany.messages
    
    case class Greet(name: String, replyTo: akka.actor.typed.ActorRef[GreetResponse])
    case class GreetResponse(message: String)
    
  • Remote Configuration: Both server and client need application.conf settings to enable remote communication. Example server config:
    akka {
      actor {
        provider = remote
        serialization-bindings {
          "com.yourcompany.messages.Greet" = jackson-json
          "com.yourcompany.messages.GreetResponse" = jackson-json
        }
      }
      remote {
        artery {
          enabled = true
          transport = tcp
          canonical.hostname = "127.0.0.1"
          canonical.port = 2552
        }
      }
    }
    
  • Client Actor Resolution: The client needs to locate the server’s Actor using its remote address. For typed Actors, here’s a quick example:
    import akka.actor.typed.ActorSystem
    import akka.actor.typed.scaladsl.AskPattern._
    import akka.util.Timeout
    import com.yourcompany.messages._
    import scala.concurrent.duration._
    
    object ClientApp extends App {
      implicit val system: ActorSystem[Nothing] = ActorSystem[Nothing]((), "client-system")
      implicit val timeout: Timeout = 5.seconds
    
      // Resolve the remote Greeter Actor
      val greeterActor = system.systemActorSelection("akka://server-system@127.0.0.1:2552/user/greeter")
    
      // Send a message and handle the response
      val response = greeterActor.ask[GreetResponse](ref => Greet("Alice", ref))
      response.onComplete {
        case Right(resp) => println(s"Server said: ${resp.message}")
        case Left(ex) => println(s"Oops, error: ${ex.getMessage}")
      }
    }
    
4. Alternative: Akka HTTP for REST Clients

If you don’t want to use Akka Remote directly, you can expose an HTTP endpoint from the server (using Akka HTTP) and have the client send JSON requests. The core module still holds the message classes—you’ll just serialize/deserialize them to JSON for HTTP communication instead of using Akka’s remote serialization.

内容的提问来源于stack exchange,提问作者Mandroid

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 07:09:26