Merge pull request #183 from Pythagora-io/v2_z

V2 z
This commit is contained in:
LeonOstrez
2025-06-03 08:09:15 +01:00
committed by GitHub
5 changed files with 114 additions and 62 deletions

View File

@@ -168,7 +168,7 @@ class Orchestrator(BaseAgent, GitMixin):
return True
async def temp_logs_for_development(self):
await self.ui.send_front_logs_headers("id5", ["e1/t1", "working"], "Building Pythagora V2!")
# await self.ui.send_front_logs_headers("id5", ["e1/t1", "working"], "Building Pythagora V2!")
# await self.ui.send_back_logs(
# [
# {
@@ -534,13 +534,13 @@ class Orchestrator(BaseAgent, GitMixin):
if prev_response.type == ResponseType.EXTERNAL_DOCS_REQUIRED:
return ExternalDocumentation(self.state_manager, self.ui, prev_response=prev_response)
if prev_response.type == ResponseType.UPDATE_SPECIFICATION:
return SpecWriter(self.state_manager, self.ui, prev_response=prev_response)
return SpecWriter(self.state_manager, self.ui, prev_response=prev_response, args=self.args)
if not state.epics:
return Wizard(self.state_manager, self.ui, process_manager=self.process_manager)
elif state.epics and not state.epics[0].get("description"):
# New project: ask the Spec Writer to refine and save the project specification
return SpecWriter(self.state_manager, self.ui, process_manager=self.process_manager)
return SpecWriter(self.state_manager, self.ui, process_manager=self.process_manager, args=self.args)
elif state.current_epic and state.current_epic.get("source") == "frontend":
# Build frontend
return Frontend(self.state_manager, self.ui, process_manager=self.process_manager)
@@ -604,7 +604,7 @@ class Orchestrator(BaseAgent, GitMixin):
return ProblemSolver(self.state_manager, self.ui)
elif current_iteration_status == IterationStatus.NEW_FEATURE_REQUESTED:
# Call Spec Writer to add the "change" requested by the user to project specification
return SpecWriter(self.state_manager, self.ui)
return SpecWriter(self.state_manager, self.ui, args=self.args)
# We have just finished the task, call Troubleshooter to ask the user to review
return Troubleshooter(self.state_manager, self.ui)

View File

@@ -67,28 +67,49 @@ class SpecWriter(BaseAgent):
await self.ui.clear_main_logs()
user_description = await self.ask_question(
"Please describe the app you want to build.",
allow_empty=False,
full_screen=True,
verbose=True,
)
description = user_description.text.strip()
# Check if initial_prompt is provided in command line arguments
if self.args and self.args.initial_prompt:
description = self.args.initial_prompt.strip()
await self.ui.send_back_logs(
[
{
"id": "setup",
"title": "",
"project_state_id": "setup",
"labels": [""],
"convo": [
{"role": "assistant", "content": "Please describe the app you want to build."},
{"role": "user", "content": description},
],
}
]
)
else:
user_description = await self.ask_question(
"Please describe the app you want to build.",
allow_empty=False,
full_screen=True,
verbose=True,
extra_info={
"chat_section_tip": "\"Some text <a href='https://example.com'>link text</a> on how to build apps with Pythagora.\""
},
)
description = user_description.text.strip()
await self.ui.send_back_logs(
[
{
"id": "setup",
"title": "",
"project_state_id": "setup",
"labels": [""],
"convo": [
{"role": "assistant", "content": "What do you want to build?"},
{"role": "user", "content": description},
],
}
]
)
await self.ui.send_back_logs(
[
{
"id": "setup",
"title": "",
"project_state_id": "setup",
"labels": [""],
"convo": [
{"role": "assistant", "content": "Please describe the app you want to build."},
{"role": "user", "content": description},
],
}
]
)
await self.ui.send_back_logs(
[
@@ -116,7 +137,7 @@ class SpecWriter(BaseAgent):
initial_prompt=description,
)
await self.ui.start_important_stream()
# await self.ui.start_important_stream()
llm_assisted_description = await llm(convo)
await self.ui.send_project_stage({"stage": ProjectStage.PROJECT_NAME})
@@ -170,12 +191,16 @@ class SpecWriter(BaseAgent):
allow_empty=False,
)
await self.send_message(
"## Refining specification\n\nPythagora is refining the specs based on your input.",
# project_state_id="setup",
)
convo = convo.template("add_to_specification", user_message=user_add_to_spec.text.strip())
if len(convo.messages) > 6:
convo.slice(1, 4)
await self.ui.start_important_stream()
# await self.ui.start_important_stream()
llm_assisted_description = await llm(convo)
convo = convo.assistant(llm_assisted_description)

View File

@@ -198,6 +198,7 @@ def parse_arguments() -> Namespace:
--extension-version: Version of the VSCode extension, if used
--use-git: Use Git for version control
--access-token: Access token
--initial-prompt: Initial prompt to automatically start a new project with 'node' stack
:return: Parsed arguments object.
"""
version = get_version()
@@ -267,6 +268,11 @@ def parse_arguments() -> Namespace:
default=8222,
help="Port for the IPC server (default: 8222)",
)
parser.add_argument(
"--initial-prompt",
help="Initial prompt to automatically start a new project with 'node' stack",
required=False,
)
return parser.parse_args()

View File

@@ -113,59 +113,78 @@ async def run_project(sm: StateManager, ui: UIBase, args) -> bool:
return success
async def start_new_project(sm: StateManager, ui: UIBase) -> bool:
async def start_new_project(sm: StateManager, ui: UIBase, args: Namespace = None) -> bool:
"""
Start a new project.
:param sm: State manager.
:param ui: User interface.
:param args: Command-line arguments.
:return: True if the project was created successfully, False otherwise.
"""
stack = await ui.ask_question(
"What do you want to build?",
allow_empty=False,
buttons={
"node": "Full stack app\n(easiest to get started)",
"swagger": "Frontend only\n(if you have backend with OpenAPI\\Swagger)",
},
buttons_only=True,
source=pythagora_source,
full_screen=True,
)
# Check if initial_prompt is provided, if so, automatically select "node"
if args and args.initial_prompt:
stack_button = "node"
await ui.send_back_logs(
[
{
"id": "setup",
"title": "",
"project_state_id": "setup",
"labels": [""],
"convo": [{"role": "assistant", "content": "What do you want to build?"}],
}
]
)
if stack.button == "other":
language = await ui.ask_question(
"What language you want to use?",
await ui.send_back_logs(
[
{
"id": "setup",
"title": "",
"project_state_id": "setup",
"labels": [""],
"convo": [{"role": "assistant", "content": "What do you want to build?"}],
}
]
)
else:
stack = await ui.ask_question(
"What do you want to build?",
allow_empty=False,
buttons={
"node": "Full stack app\n(easiest to get started)",
"swagger": "Frontend only\n(if you have backend with OpenAPI\\Swagger)",
},
buttons_only=True,
source=pythagora_source,
full_screen=True,
)
await telemetry.trace_code_event(
"stack-choice-other",
{"language": language.text},
await ui.send_back_logs(
[
{
"id": "setup",
"title": "",
"project_state_id": "setup",
"labels": [""],
"convo": [{"role": "assistant", "content": "What do you want to build?"}],
}
]
)
await ui.send_message("Thank you for submitting your request to support other languages.")
return False
if stack.button == "other":
language = await ui.ask_question(
"What language you want to use?",
allow_empty=False,
source=pythagora_source,
full_screen=True,
)
await telemetry.trace_code_event(
"stack-choice-other",
{"language": language.text},
)
await ui.send_message("Thank you for submitting your request to support other languages.")
return False
stack_button = stack.button
await telemetry.trace_code_event(
"stack-choice",
{"language": stack.button},
{"language": stack_button},
)
project_state = await sm.create_project(project_type=stack.button)
project_state = await sm.create_project(project_type=stack_button)
return project_state is not None
@@ -189,8 +208,9 @@ async def run_pythagora_session(sm: StateManager, ui: UIBase, args: Namespace):
await print_convo(ui, convo)
else:
# await ui.send_front_logs_headers("setup", ["E0 / T0", "Setup", "working"], "")
await ui.send_message("Starting Pythagora ...", source=pythagora_source)
success = await start_new_project(sm, ui)
success = await start_new_project(sm, ui, args)
if not success:
return False

View File

@@ -63,6 +63,7 @@ def test_parse_arguments(mock_ArgumentParser):
"--use-git",
"--access-token",
"--no-auto-confirm-breakdown",
"--initial-prompt",
}
parser.parse_args.assert_called_once_with()