Skip to content

Development: Initialize new Hyperion module for programming exercise creation assistance and migrate functionality from Iris #11047

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 20 commits into
base: develop
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 19 commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
46b6282
feat: Add Hyperion integration for problem statement rewriting and co…
FelixTJDietrich Jun 22, 2025
b474286
feat: Update build configuration for Edutelligence Hyperion integrati…
FelixTJDietrich Jun 24, 2025
14aaa91
feat: Add GitHub authentication for Maven repositories in Dockerfile …
FelixTJDietrich Jun 24, 2025
8f50919
feat: Implement base service for Hyperion gRPC operations with except…
FelixTJDietrich Jun 24, 2025
2bd5aaf
fix: Use secrets for GITHUB_TOKEN in Docker build args
FelixTJDietrich Jun 24, 2025
5487471
chore: trigger CI - test Hyperion integration
FelixTJDietrich Jun 24, 2025
4a2b2ac
fix: use github.token instead of secrets.GITHUB_TOKEN in reusable wor…
FelixTJDietrich Jun 24, 2025
17abce5
fix: inherit secrets for Docker build in GitHub Actions workflow
FelixTJDietrich Jun 24, 2025
0e70993
TODO: REMOVE!
FelixTJDietrich Jun 24, 2025
110571a
fix: replace reusable Docker workflow with embedded one for proper Gi…
FelixTJDietrich Jun 24, 2025
16ee5b5
fix: update Docker build process to use reusable workflow and inherit…
FelixTJDietrich Jun 24, 2025
b11dfcd
fix: update Docker build to use github.GITHUB_TOKEN for authentication
FelixTJDietrich Jun 24, 2025
07327be
fix: update Docker build to use secrets.GITHUB_TOKEN for authentication
FelixTJDietrich Jun 24, 2025
d809307
fix: refactor Docker build process to use matrix strategy and improve…
FelixTJDietrich Jun 24, 2025
edcd30e
fix: refine conditional checks for pull request repository validation…
FelixTJDietrich Jun 24, 2025
fc5cd5e
fix: enable Hyperion profile by default and remove deprecated Hyperio…
FelixTJDietrich Jun 24, 2025
a3634d7
switch from java client dependency to plugin integration with spec
FelixTJDietrich Jun 27, 2025
01bd1d6
Merge branch 'develop' into feature/hyperion/initialize-service
FelixTJDietrich Jun 27, 2025
48b97a0
add generated files and spec to module
FelixTJDietrich Jun 28, 2025
a1072be
use grpc starter
FelixTJDietrich Jun 28, 2025
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
3 changes: 3 additions & 0 deletions .github/CODEOWNERS
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
/src/main/java/de/tum/cit/aet/artemis/atlas @ls1intum/atlas-maintainers
/src/main/java/de/tum/cit/aet/artemis/buildagent @ls1intum/programming-maintainers
/src/main/java/de/tum/cit/aet/artemis/communication @ls1intum/communication-maintainers
/src/main/java/de/tum/cit/aet/artemis/hyperion @ls1intum/hyperion-maintainers
/src/main/java/de/tum/cit/aet/artemis/iris @ls1intum/iris-maintainers
/src/main/java/de/tum/cit/aet/artemis/lecture @ls1intum/lectures-maintainers
/src/main/java/de/tum/cit/aet/artemis/lti @ls1intum/lti-maintainers
Expand All @@ -31,6 +32,7 @@
/src/main/webapp/app/atlas @ls1intum/atlas-maintainers
/src/main/webapp/app/buildagent @ls1intum/programming-maintainers
/src/main/webapp/app/communication @ls1intum/communication-maintainers
/src/main/webapp/app/hyperion @ls1intum/hyperion-maintainers
/src/main/webapp/app/iris @ls1intum/iris-maintainers
/src/main/webapp/app/lecture @ls1intum/lectures-maintainers
/src/main/webapp/app/lti @ls1intum/lti-maintainers
Expand All @@ -44,6 +46,7 @@
/src/test/java/de/tum/cit/aet/artemis/atlas @ls1intum/atlas-maintainers
/src/test/java/de/tum/cit/aet/artemis/buildagent @ls1intum/programming-maintainers
/src/test/java/de/tum/cit/aet/artemis/communication @ls1intum/communication-maintainers
/src/test/java/de/tum/cit/aet/artemis/hyperion @ls1intum/hyperion-maintainers
/src/test/java/de/tum/cit/aet/artemis/iris @ls1intum/iris-maintainers
/src/test/java/de/tum/cit/aet/artemis/lecture @ls1intum/lectures-maintainers
/src/test/java/de/tum/cit/aet/artemis/lti @ls1intum/lti-maintainers
Expand Down
6 changes: 6 additions & 0 deletions .github/issue-labeler.yml
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,12 @@ iris:
- \b(?<!\S)ai(?!\S)\b
- caseSensitive: false

hyperion:
- hyperion
- consistency check
- exercise generation
- caseSensitive: false

lecture:
- lecture
- attachment
Expand Down
7 changes: 7 additions & 0 deletions .github/labeler.yml
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,13 @@ iris:
- src/test/java/de/tum/cit/aet/artemis/iris/**/*
- src/main/webapp/app/iris/**/*

hyperion:
- changed-files:
- any-glob-to-any-file:
- src/main/java/de/tum/cit/aet/artemis/hyperion/**/*
- src/test/java/de/tum/cit/aet/artemis/hyperion/**/*
- src/main/webapp/app/hyperion/**/*

lecture:
- changed-files:
- any-glob-to-any-file:
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@ Artemis integrates with the [EduTelligence suite](https://github.com/ls1intum/ed

* **Iris** - AI Virtual Tutor powered by Pyris for intelligent student assistance
* **Athena** - Automated assessment system for text, modeling, and programming exercises
* **Hyperion** - AI-powered programming exercise creation assistance

Additional services are available in the EduTelligence suite for advanced deployments. For detailed information about all available services, please refer to the [EduTelligence repository](https://github.com/ls1intum/edutelligence).

Expand Down Expand Up @@ -145,6 +146,7 @@ The following members of the project management team are responsible for specifi
| Atlas | Maximilian Anzinger ([@maximiliananzinger](https://github.com/maximiliananzinger)) |
| Iris | Patrick Bassner ([@bassner](https://github.com/bassner)) |
| Athena | Maximilian Sölch ([@maximiliansoelch](https://github.com/maximiliansoelch)) |
| Hyperion | Felix Dietrich ([@FelixTJDietrich](https://github.com/FelixTJDietrich)) |
| Tutorial Groups | Ramona Beinstingel ([@rabeatwork](https://github.com/rabeatwork)) |
| Plagiarism checks | Markus Paulsen ([@MarkusPaulsen](https://github.com/MarkusPaulsen)) |
| LTI | Maximilian Anzinger ([@maximiliananzinger](https://github.com/maximiliananzinger)) |
Expand Down
80 changes: 79 additions & 1 deletion build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ plugins {
id "org.liquibase.gradle" version "${liquibase_plugin_version}"
id "org.owasp.dependencycheck" version "12.1.3"
id "org.springframework.boot" version "${spring_boot_version}"
id "com.google.protobuf" version "${protobuf_plugin_version}"
}

group = "de.tum.cit.aet.artemis"
Expand Down Expand Up @@ -151,6 +152,71 @@ configurations.configureEach {
exclude group: "commons-configuration", module: "commons-configuration"
}

// Protobuf Configuration for gRPC Integration
protobuf {
generatedFilesBaseDir = "$projectDir/src"

protoc {
artifact = "com.google.protobuf:protoc:${protobuf_version}"
}
plugins {
grpc {
artifact = "io.grpc:protoc-gen-grpc-java:${grpc_version}"
}
}
generateProtoTasks {
all().each { task ->
task.builtins {
java {
outputSubDir = 'main/java'
}
}
task.plugins {
grpc {
outputSubDir = 'main/java'
}
}
}
}
}

// Task to move generated files to correct location
tasks.register("moveGeneratedFiles") {
doLast {
// Find all generated directories under src/main/main/java/de/tum/cit/aet/artemis/*/generated
def incorrectMainDir = file("src/main/main")
if (incorrectMainDir.exists()) {
def artemisPath = file("src/main/main/java/de/tum/cit/aet/artemis")
if (artemisPath.exists()) {
artemisPath.listFiles().each { moduleDir ->
if (moduleDir.isDirectory()) {
def generatedDir = new File(moduleDir, "generated")
if (generatedDir.exists()) {
def moduleName = moduleDir.name
def targetDir = file("src/main/java/de/tum/cit/aet/artemis/${moduleName}/generated")

println "Moving generated files for module: ${moduleName}"
targetDir.parentFile.mkdirs()
ant.move(todir: targetDir) {
fileset(dir: generatedDir)
}
}
}
}
}

// Clean up the incorrect main directory after moving all files
incorrectMainDir.deleteDir()
}
}
}

// Make sure generated files are moved after generation
generateProto.finalizedBy moveGeneratedFiles

compileJava.dependsOn generateProto
compileTestJava.dependsOn generateProto

dependencies {

// Required by Spring cloud
Expand Down Expand Up @@ -284,6 +350,13 @@ dependencies {
// Avoid outdated version of netty to prevent security issues
implementation("net.minidev:json-smart") { version {strictly "2.5.2" } }

// gRPC Client Dependencies
implementation platform("io.grpc:grpc-bom:${grpc_version}")
implementation 'io.grpc:grpc-protobuf'
implementation 'io.grpc:grpc-stub'
implementation 'io.grpc:grpc-netty-shaded'
implementation "com.google.protobuf:protobuf-java:${protobuf_version}"
implementation 'javax.annotation:javax.annotation-api:1.3.2'

// Required for synchronization between nodes and build agents (LocalCI)
implementation "com.hazelcast:hazelcast:${hazelcast_version}"
Expand Down Expand Up @@ -406,8 +479,8 @@ dependencies {
runtimeOnly "commons-beanutils:commons-beanutils:1.11.0"
checkstyle "commons-beanutils:commons-beanutils:1.11.0"


implementation "com.google.errorprone:error_prone_annotations:2.39.0"
implementation "io.grpc:grpc-services:${grpc_services_version}"

// NOTE: we want to keep the same unique version for all configurations, implementation and annotationProcessor
implementation("net.bytebuddy:byte-buddy") { version { strictly byte_buddy_version } }
Expand Down Expand Up @@ -451,6 +524,11 @@ dependencies {
testImplementation "org.apache.maven.surefire:surefire-report-parser:3.5.3"
testImplementation "io.zonky.test:embedded-database-spring-test:2.6.0"

// gRPC testing dependencies
testImplementation "io.grpc:grpc-testing:${grpc_version}"
testImplementation "io.grpc:grpc-inprocess:${grpc_version}"
testImplementation "io.grpc:grpc-services:${grpc_services_version}"

testImplementation "com.tngtech.archunit:archunit:1.4.1"
testImplementation "org.skyscreamer:jsonassert:1.5.3"

Expand Down
2 changes: 1 addition & 1 deletion docs/dev/development-process/development-process.rst
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ Naming Conventions for GitHub Pull Requests

1. Possible feature tags are: ``Programming exercises``, ``Integrated code lifecycle``, ``Quiz exercises``, ``Modeling exercises``, ``Text exercises``, ``File upload exercises``, ``Exam mode``,
``Grading``, ``Assessment``, ``Communication``, ``Notifications``, ``Team exercises``, ``Lectures``, ``Integrated markdown editor``, ``Plagiarism checks``, ``Learning analytics``,
``Adaptive learning``, ``Learning path``, ``Tutorial groups``, ``Iris``, ``Scalability``, ``Usability``, ``Performance``, ``Infrastructure``, ``Mobile apps``.
``Adaptive learning``, ``Learning path``, ``Tutorial groups``, ``Iris``, ``Hyperion``, ``Scalability``, ``Usability``, ``Performance``, ``Infrastructure``, ``Mobile apps``.
2. If the change is not visible to end users, or it is a pure development or test improvement, we use the term ``Development``:.
3. Everything else belongs to the ``General`` category.

Expand Down
58 changes: 58 additions & 0 deletions docs/dev/setup/server.rst
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,13 @@ You only need to modify them if your specific work or production environments re
athena:
# If you want to use Athena, refer to the dedicated configuration section. Under Administration Guide, Setup of Extension Services.

hyperion:
# If you want to use Hyperion for programming exercise creation assistance, configure the service connection below.
# For production, enable TLS and configure certificates. See Hyperion Service section below.
host: localhost
port: 50051
use-tls: false

**Note:**
If you use a password for authentication, update it in ``gradle/liquibase.gradle``.

Expand Down Expand Up @@ -106,6 +113,8 @@ module replacement in the client.
``dev,jenkins,localvc,artemis,scheduling,core,atlas,local``.
* **Artemis (Server, LocalVC & LocalCI, Athena):** The server will be started separated from the client with ``athena`` profile and Local VC / CI enabled
(see `Athena Service <#athena-service>`__).
* **Artemis (Server, LocalVC & LocalCI, Hyperion):** The server will be started separated from the client with ``hyperion`` profile and Local VC / CI enabled
(see `Hyperion Service <#hyperion-service>`__).
* **Artemis (Server, LocalVC & LocalCI, Theia):** The server will be started separated from the client with ``theia`` profile and Local VC / CI enabled.
* **Artemis (BuildAgent):** The server will be started separated from the client with the profiles ``buildagent,local``.
This configuration is used to run the build agent for the local CI. This configuration is rarely needed for development.
Expand Down Expand Up @@ -250,3 +259,52 @@ sure to pass the active profiles to the ``gradlew`` command like this:
.. code:: bash

./gradlew bootRun --args='--spring.profiles.active=dev,jenkins,localvc,artemis,scheduling'

.. _hyperion-service:

Hyperion Service
^^^^^^^^^^^^^^^^

Hyperion is an AI-powered Edutelligence microservice for programming exercise creation assistance. To enable Hyperion:

1. **Setup Hyperion Service** (external dependency)

- Deploy Hyperion service separately (see Hyperion documentation)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please add a link to the Hyperion documentation here.

- Ensure it's accessible from Artemis server

2. **Configure Connection**

Update ``application-local.yml`` (for development):

.. code-block:: yaml

artemis:
hyperion:
host: localhost # Hyperion service host
port: 50051 # Hyperion gRPC port
use-tls: false # Disable TLS for development

For production, enable TLS in ``application-artemis.yml``:

.. code-block:: yaml

artemis:
hyperion:
host: hyperion.domain.com
port: 50051
use-tls: true
client-cert-path: "/certs/artemis-client.crt"
client-key-path: "/certs/artemis-client.key"
server-ca-path: "/certs/hyperion-ca.crt"

3. **Enable Profile**

Add ``hyperion`` to active profiles:

.. code-block:: bash

./gradlew bootRun --args='--spring.profiles.active=dev,localci,localvc,artemis,hyperion'

4. **Verify Setup**

Check health endpoint: ``http://localhost:8080/actuator/health/hyperion``
6 changes: 6 additions & 0 deletions gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,12 @@ netty_version=4.1.118.Final
mysql_version=9.3.0
micrometer_version=1.15.1

# protobuf and gRPC versions for Edutelligence integration
protobuf_plugin_version=0.9.5
protobuf_version=4.31.1
grpc_version=1.73.0
grpc_services_version=1.71.0

# testing
# make sure both versions are compatible
junit_version=5.13.2
Expand Down
3 changes: 3 additions & 0 deletions src/main/java/de/tum/cit/aet/artemis/ArtemisApp.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package de.tum.cit.aet.artemis;

import static de.tum.cit.aet.artemis.core.config.Constants.PROFILE_HYPERION;
import static de.tum.cit.aet.artemis.core.config.Constants.UPLOADS_FILE_PATH_DEFAULT;
import static de.tum.cit.aet.artemis.core.config.Constants.UPLOADS_FILE_PATH_PROPERTY_NAME;
import static tech.jhipster.config.JHipsterConstants.SPRING_PROFILE_DEVELOPMENT;
Expand Down Expand Up @@ -78,6 +79,8 @@ public void initApplication() {
public static void main(String[] args) {
SpringApplication app = new SpringApplication(ArtemisApp.class);
DefaultProfileUtil.addDefaultProfile(app);
// Enable Hyperion profile by default TODO: REMOVE!!!!!!!!!!!!!!!!!!!!!!!!!!
app.setAdditionalProfiles(PROFILE_HYPERION);
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

TODO REMOVE

Comment on lines +82 to +83
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Remove temporary development code before production deployment.

This temporary code enables the Hyperion profile by default in the main application class, which could have unintended consequences in production environments. The excessive exclamation marks in the TODO comment also indicate this is not production-ready code.

Consider these alternatives:

  1. Enable the profile through environment-specific configuration files
  2. Use command-line arguments or environment variables for profile activation
  3. Create a separate development configuration class

Apply this diff to remove the temporary code:

-        // Enable Hyperion profile by default TODO: REMOVE!!!!!!!!!!!!!!!!!!!!!!!!!!
-        app.setAdditionalProfiles(PROFILE_HYPERION);

Then configure the profile activation through proper Spring Boot configuration mechanisms (application.properties, environment variables, or command-line arguments).

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
// Enable Hyperion profile by default TODO: REMOVE!!!!!!!!!!!!!!!!!!!!!!!!!!
app.setAdditionalProfiles(PROFILE_HYPERION);
🤖 Prompt for AI Agents
In src/main/java/de/tum/cit/aet/artemis/ArtemisApp.java around lines 82 to 83,
remove the temporary code that enables the Hyperion profile by default using
app.setAdditionalProfiles(PROFILE_HYPERION). Instead, configure profile
activation through Spring Boot's standard mechanisms such as
environment-specific application.properties files, command-line arguments, or
environment variables to avoid unintended effects in production.

var context = app.run(args);
Environment env = context.getEnvironment();
String fileUploadPath = env.getProperty(UPLOADS_FILE_PATH_PROPERTY_NAME);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -318,6 +318,11 @@ public final class Constants {
*/
public static final String PROFILE_ATHENA = "athena";

/**
* The name of the Spring profile used for Hyperion functionality.
*/
public static final String PROFILE_HYPERION = "hyperion";

/**
* The name of the Spring profile used for Athena functionality.
*/
Expand Down
Loading
Loading