diff --git a/kyo-llm-macros/shared/src/main/scala/kyo/llm/json/Json.scala b/kyo-llm-macros/shared/src/main/scala/kyo/llm/json/Json.scala index 6c6ee0b82..7bca49a88 100644 --- a/kyo-llm-macros/shared/src/main/scala/kyo/llm/json/Json.scala +++ b/kyo-llm-macros/shared/src/main/scala/kyo/llm/json/Json.scala @@ -29,7 +29,7 @@ object Json extends JsonDerive { def fromZio[T](z: ZSchema[T]) = new Json[T] { - val zSchema = z + val zSchema = z lazy val schema: Schema = Schema(z) private lazy val decoder = JsonCodec.jsonDecoder(z) private lazy val encoder = JsonCodec.jsonEncoder(z) diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/agents.scala b/kyo-llm/shared/src/main/scala/kyo/llm/agents.scala index 35225c4c7..6a06d7d59 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/agents.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/agents.scala @@ -23,7 +23,7 @@ import zio.Chunk import zio.schema.validation.Validation import scala.collection.immutable.ListMap -package object agents { +package object agents { abstract class Agent { @@ -62,29 +62,31 @@ package object agents { val fields = l.map { t => import zio.schema.Schema._ Field[ListMap[String, Any], Any]( - t.name, - t.zSchema.asInstanceOf[ZSchema[Any]], - Chunk.empty, - Validation.succeed, - identity, - (_, _) => ListMap.empty) + t.name, + t.zSchema.asInstanceOf[ZSchema[Any]], + Chunk.empty, + Validation.succeed, + identity, + (_, _) => ListMap.empty + ) } - ZSchema.record(TypeId.fromTypeName(name), FieldSet(fields:_*)).asInstanceOf[ZSchema[T]] + ZSchema.record(TypeId.fromTypeName(name), FieldSet(fields: _*)).asInstanceOf[ZSchema[T]] } - val (opening, closing) = thoughts.partition(_.opening) + val (opening, closing) = thoughts.partition(_.opening) implicit val o: ZSchema[opening.type] = schema("OpeningThoughts", opening) implicit val c: ZSchema[closing.type] = schema("ClosingThoughts", closing) - implicit val i: ZSchema[In] = info.input.zSchema + implicit val i: ZSchema[In] = info.input.zSchema Json.schema[Agents.Request[opening.type, In, closing.type]] } - private[kyo] def handle(ai: AI, v: String): String < AIs = + private[kyo] def handle(ai: AI, v: String): String < AIs = { implicit def s: ZSchema[In] = info.input.zSchema Json.decode[Agents.RequestPayload[In]](v).map { res => - Listeners.observe(res.actionNarrationToBeShownToTheUser) { + Listeners.observe(res.shortActionNarrationToBeShownToTheUser) { run(ai, res.agentInput).map(info.output.encode) } } + } } object Agents { @@ -102,39 +104,23 @@ package object agents { """ ) case class Request[Opening, T, Closing]( - // @desc("A short text to provide a status update to the user.") - actionNarrationToBeShownToTheUser: String, - openingThoughts: Request.OpeningThoughts[Opening], - `List opening thoughts`: String, - `Strategy to adhere to all opening thoughts`: String, - `agentInput must be not empty and complete, it's only thing the user will see`: Boolean, - // @desc("Do not skip! String fields are text, not json. Change the tone as if you're addressing the user. Analyze and leverage the thoughts so far.") + strictlyFollowTheJsonSchema: true, + `Even when the the field name is a text like here`: true, + `Text field names function as an inner-dialog reasoning mechanism`: true, + openingThoughts: Opening, + `Summary of all opening thoughts`: String, + `I'll change the tone as if I'm addressing the user`: true, + `I won't have another oportunity to elaborate further`: true, + `agentInput is the only field visible to the user`: true, agentInput: T, - closingThoughts: Request.ClosingThoughts[Closing] + `agentInput is complete, elaborate, and fully satisfies the user's resquest`: true, + closingThoughts: Closing, + shortActionNarrationToBeShownToTheUser: String, + `I will not generate a sequence of several spaces or new line charaters`: true ) - object Request { - case class OpeningThoughts[T]( - strictlyFollowTheJsonSchema: Boolean, - `Even when the the field name is a text like here`: Boolean, - // @desc("Make sure to generate all required fields by the json schema.") - `I understand text field names function as an inner-dialog reasoning mechanism`: Boolean, - additionalOpeningThoughts: T, - `Do not output json in string fields`: Boolean, - `I'll change the tone as if I'm addressing the user`: Boolean, - `Next json schema fields to generate, which include agentInput`: String - ) - case class ClosingThoughts[T]( - `The opening thoughts were considered`: Boolean, - `The input is complete and follows the json schema`: Boolean, - additionalClosingThoughts: T, - // @desc("There's a common issue where you output many new line characters after the json.") - `I will not generate a sequence of several new line charaters`: Boolean - ) - } - case class RequestPayload[T]( - actionNarrationToBeShownToTheUser: String, + shortActionNarrationToBeShownToTheUser: String, agentInput: T ) @@ -165,7 +151,7 @@ package object agents { "Call this agent with the result." ) - override def thoughts: List[Thought.Info] = + override def thoughts: List[Thought.Info] = _thoughts def run(input: T) = diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/configs.scala b/kyo-llm/shared/src/main/scala/kyo/llm/configs.scala index 581c10ee3..744899ad8 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/configs.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/configs.scala @@ -62,7 +62,7 @@ object configs { apiKey, apiOrg, Model.gpt4_turbo, - 0.2, + 0.7, None, None, Meters.initNoop, diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Brainstorm.scala b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Brainstorm.scala index 7a3c1af9d..048c7c4fe 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Brainstorm.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Brainstorm.scala @@ -2,18 +2,8 @@ package kyo.llm.thoughts import kyo.llm.ais._ -@desc( - p""" - The Brainstorm thought fosters innovation and divergent thinking in AI. - - Combines creative problem solving with design thinking. - - Encourages lateral thinking and ideation for novel concepts. - """ -) case class Brainstorm( `Reflect on the user's intent`: String, `Apply lateral thinking for new perspectives`: String, - `Elaborate on new perspectives`: String, - `Consider alternative solutions`: String, - `Create innovative approaches`: String, - `Elaborate on innovative solutions`: String + `Consider alternative innovative solutions`: String ) extends Thought.Opening diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Contextualize.scala b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Contextualize.scala index c89dabb6d..a83e8c72e 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Contextualize.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Contextualize.scala @@ -2,18 +2,8 @@ package kyo.llm.thoughts import kyo.llm.ais._ -@desc( - p""" - The Contextualize thought involves analyzing the previous interactions to - inform your plans on how to handle the user's request. - - Assesses the relationship of input to previous discussions or knowledge. - - Identifies broader context relevant to the input. - - Relevant techniques: Context Analysis, Pattern Recognition. - """ -) case class Contextualize( `Determine the core message or question in the input`: String, `Assess how the current input relates to previous discussions or knowledge`: String, - `Identify the broader context or background relevant to the input`: String, `Identify any ambiguous or unclear aspects that need further clarification`: String ) extends Thought.Opening diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Elaborate.scala b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Elaborate.scala index 20a50f1ca..a12557aa7 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Elaborate.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Elaborate.scala @@ -2,10 +2,8 @@ package kyo.llm.thoughts import kyo.llm.ais._ -@desc( - "All text and any other field from this point on must be complete and with **as much detail as possible**. Perfer long texts." -) case class Elaborate( - `I'll generate a json that is complete and as detailed as possible`: Boolean, - `Stragegy to generate a complete and well elaborated output`: String + `Generate a json that is complete and as detailed as possible`: true, + `Strategy to elaborate outputs and generate long texts`: String, + `I'll elaborate the outputs and use bulleted lists if appropiate`: true ) extends Thought.Opening diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Humorize.scala b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Humorize.scala index 99e03e3cf..586a7531a 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Humorize.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Humorize.scala @@ -2,17 +2,8 @@ package kyo.llm.thoughts import kyo.llm.ais._ -@desc( - p""" - The Humorize thought directs the LLM in crafting humor within a given context. - - Explores the context for potential comedic elements. - - Develops humor that is engaging, witty, and contextually relevant. - - Ensures that the humor is appropriate and sensitive to the audience. - """ -) case class Humorize( - `Context exploration for humor`: String, `Comedic elements identified`: String, `Strategy for humorous content creation`: String, `Appropriateness and audience sensitivity`: String -) extends Thought.Opening \ No newline at end of file +) extends Thought.Opening diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Reduce.scala b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Reduce.scala index 241d92b09..783a1ca0a 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Reduce.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Reduce.scala @@ -9,16 +9,6 @@ import scala.util.Random import kyo.consoles.Consoles import kyo.llm.agents.Agent -@desc( - p""" - The Reduce thought allows for detailed tracking and explanation of each step in the expression reduction process. - - Includes detailed rule descriptions and expression transformations. - - Tracks intermediate expressions and sub-expressions. - - Normalizes input expression and iteratively simplifies it. - - **None of the fields can be empty** - - **No empty arrays and no empty strings** - """ -) case class Reduce[Expr, Result]( initialExpression: Expr, `Reduce steps can not be empty`: Boolean, @@ -27,16 +17,6 @@ case class Reduce[Expr, Result]( `Reduce steps and result are not empty`: Boolean ) extends Thought.Opening -@desc( - p""" - The Reduce thought allows for detailed tracking and explanation of each step in the expression reduction process. - - Includes detailed rule descriptions and expression transformations. - - Tracks intermediate expressions and sub-expressions. - - Normalizes input expression and iteratively simplifies it. - - **None of the fields can be empty** - - **No empty arrays and no empty strings** - """ -) case class ReduceStep[Expr]( ruleDescription: String, inputExpression: Expr, diff --git a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Repair.scala b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Repair.scala index dfbe162fe..ca5e2a942 100644 --- a/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Repair.scala +++ b/kyo-llm/shared/src/main/scala/kyo/llm/thoughts/Repair.scala @@ -2,17 +2,8 @@ package kyo.llm.thoughts import kyo.llm.ais._ -@desc( - p""" - The Repair thought guides the LLM in addressing and learning from errors. - - Analyzes causes of past failures. - - Develops strategies to prevent future errors. - - Encourages critical evaluation and adaptive learning. - """ -) case class Repair( `Check for failures from function calls`: String, `Identify causes of the failures`: String, - `Formulate strategies to prevent future errors`: String, `Detail corrective measures for improvement`: String ) extends Thought.Opening diff --git a/kyo-llm/shared/src/test/scala/kyo/llm/thoughts/ttt.scala b/kyo-llm/shared/src/test/scala/kyo/llm/thoughts/ttt.scala index b7c12338e..4fac143ba 100644 --- a/kyo-llm/shared/src/test/scala/kyo/llm/thoughts/ttt.scala +++ b/kyo-llm/shared/src/test/scala/kyo/llm/thoughts/ttt.scala @@ -10,15 +10,17 @@ import kyo.llm.configs.Model object ttt extends KyoLLMApp { run { - for { - ai <- AIs.init - _ <- ai.thought[Contextualize] - _ <- ai.thought[Brainstorm] - // _ <- ai.thought[Humorize] - // _ <- ai.thought[Elaborate] - _ <- ai.thought[RolePlay["You're a funny person that uses suffer lingo"]] - } yield ai.gen[String]( - "What could be the most unexpected things that could happen as AIs evolve?" - ) + AIs.parallel(List.fill(1) { + for { + ai <- AIs.init + _ <- ai.thought[RolePlay["You're an expert and a community lead in Scala"]] + _ <- ai.thought[Contextualize] + _ <- ai.thought[Brainstorm] + _ <- ai.thought[Humorize] + _ <- ai.thought[Elaborate] + } yield ai.gen[String]( + "What's the future of Scala? Why does it have so many dramas?" + ) + }).map(_.mkString("\n============================\n")) } }