Volle Mindflux-App ins Deploy-Repo übernehmen

Ersetzt das Hello-World-Gerüst durch die vollständige Anwendung
(com.example.mindflux: 64 Klassen, Thymeleaf-Templates, Static-Assets,
Flyway V1–V6). Deploy-Infrastruktur (.gitea, Dockerfile) bleibt erhalten.

- pom: volle Abhängigkeiten (Security, Thymeleaf, JPA, Flyway), Spring Boot 3.4.4 / Java 17
- docker-compose: SPRING_DATASOURCE_* unverändert; App lauscht auf 8080
  (nginx -> mindflux:8080); Uploads-Volume; Admin-Passwörter via Gitea-Secrets
- Workflow: Deploy-Step injiziert MINDFLUX_ADMIN*_PASSWORD aus Secrets
- .dockerignore ergänzt; Hello-World (com.mindflux) und Test-Datei 'main' entfernt

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
AliceDarkest
2026-06-26 14:51:30 +02:00
parent f3309c1574
commit 9022961762
185 changed files with 22772 additions and 142 deletions
@@ -0,0 +1,12 @@
package com.example.mindflux;
import org.springframework.boot.CommandLineRunner;
import org.springframework.stereotype.Component;
@Component
public class AppStartCheck implements CommandLineRunner {
@Override
public void run(String... args) {
System.out.println("✅ App läuft. Sicherheitsmodul sollte aktiv sein.");
}
}
@@ -1,10 +1,11 @@
package com.mindflux;
package com.example.mindflux;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class MindfluxApplication {
public static void main(String[] args) {
SpringApplication.run(MindfluxApplication.class, args);
}
@@ -0,0 +1,60 @@
package com.example.mindflux.config;
import com.example.mindflux.model.User;
import com.example.mindflux.repository.UserRepository;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.CommandLineRunner;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
@Configuration
public class AdminSetup {
@Value("${MINDFLUX_ADMIN_USERNAME:admin}")
private String adminUsername;
@Value("${MINDFLUX_ADMIN_EMAIL:admin@mindflux.de}")
private String adminEmail;
@Value("${MINDFLUX_ADMIN_PASSWORD:}")
private String adminPassword;
// Optionaler zweiter Bootstrap-Admin. Wird nur angelegt, wenn Username + Passwort gesetzt sind.
@Value("${MINDFLUX_ADMIN2_USERNAME:}")
private String admin2Username;
@Value("${MINDFLUX_ADMIN2_EMAIL:}")
private String admin2Email;
@Value("${MINDFLUX_ADMIN2_PASSWORD:}")
private String admin2Password;
@Bean
public CommandLineRunner createAdmin(UserRepository userRepo, BCryptPasswordEncoder passwordEncoder) {
return args -> {
createAdminIfAbsent(userRepo, passwordEncoder, adminUsername, adminEmail, adminPassword);
createAdminIfAbsent(userRepo, passwordEncoder, admin2Username, admin2Email, admin2Password);
};
}
private void createAdminIfAbsent(UserRepository userRepo, BCryptPasswordEncoder passwordEncoder,
String username, String email, String password) {
if (username == null || username.isBlank()) {
return; // Admin-Slot nicht konfiguriert -> still überspringen.
}
if (password == null || password.isBlank()) {
System.out.println("Kein Bootstrap-Admin erstellt: Passwort für '" + username + "' ist nicht gesetzt.");
return;
}
if (userRepo.findByUsername(username).isEmpty()) {
User admin = new User();
admin.setUsername(username);
admin.setEmail(email);
admin.setPassword(passwordEncoder.encode(password));
admin.setRole("ADMIN");
userRepo.save(admin);
System.out.println("Bootstrap-Admin erstellt: " + username);
}
}
}
@@ -0,0 +1,65 @@
package com.example.mindflux.config;
import com.example.mindflux.model.User;
import com.example.mindflux.repository.UserRepository;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.configuration.AuthenticationConfiguration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.core.userdetails.*;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.web.SecurityFilterChain;
@Configuration
public class SecurityConfig {
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
http
.authorizeHttpRequests(auth -> auth
.requestMatchers("/", "/login", "/register", "/css/**", "/js/**", "/img/**").permitAll()
.requestMatchers("/admin/**").hasRole("ADMIN") // NEU: Adminbereich absichern
.requestMatchers("/api/users/**").hasRole("ADMIN")
.anyRequest().authenticated()
)
.formLogin(form -> form
.loginPage("/") // login.html liegt auf "/"
.loginProcessingUrl("/login")
.defaultSuccessUrl("/dashboard", true)
.failureUrl("/?error") // zeigt Loginfehler an
.permitAll()
)
.logout(logout -> logout
.logoutSuccessUrl("/?logout")
.permitAll()
)
.csrf(csrf -> csrf.disable()); // optional deaktivieren bei Custom-Logik/API-Nutzung
return http.build();
}
@Bean
public UserDetailsService userDetailsService(UserRepository userRepo) {
return username -> {
User user = userRepo.findByUsername(username)
.orElseThrow(() -> new UsernameNotFoundException("Benutzer nicht gefunden"));
return org.springframework.security.core.userdetails.User
.withUsername(user.getUsername())
.password(user.getPassword())
.roles(user.getRole()) // Achtung: Nur ein String, z.B. "USER" oder "ADMIN"
.build();
};
}
@Bean
public BCryptPasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder();
}
@Bean
public AuthenticationManager authenticationManager(AuthenticationConfiguration config) throws Exception {
return config.getAuthenticationManager();
}
}
@@ -0,0 +1,127 @@
package com.example.mindflux.config;
import com.example.mindflux.model.TechtacularAnswer;
import com.example.mindflux.model.TechtacularCategory;
import com.example.mindflux.model.TechtacularQuestion;
import com.example.mindflux.repository.TechtacularCategoryRepository;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.boot.CommandLineRunner;
import org.springframework.core.io.ClassPathResource;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;
import java.util.HashSet;
import java.util.Set;
/**
* Befüllt TechTacular einmalig (wenn leer) aus der kuratierten Inhaltsdatei
* techtacular/content.json. Format: Jeopardy umgekehrt – pro Hinweis eine Aussage
* ("clue") und der gesuchte Begriff ("solution", = richtige Antwort) plus Distraktoren.
*/
@Component
public class TechtacularSeeder implements CommandLineRunner {
private final TechtacularCategoryRepository categoryRepository;
private final ObjectMapper objectMapper;
public TechtacularSeeder(TechtacularCategoryRepository categoryRepository, ObjectMapper objectMapper) {
this.categoryRepository = categoryRepository;
this.objectMapper = objectMapper;
}
@Override
@Transactional
public void run(String... args) {
if (categoryRepository.count() > 0) {
return; // schon befüllt
}
try {
JsonNode root = objectMapper.readTree(new ClassPathResource("techtacular/content.json").getInputStream());
JsonNode categories = root.get("categories");
if (categories == null || !categories.isArray()) {
System.out.println("⚠️ TechTacular-Seed: content.json ohne 'categories'.");
return;
}
Set<String> usedSlugs = new HashSet<>();
int order = 1;
int catCount = 0;
int clueCount = 0;
for (JsonNode catNode : categories) {
String title = catNode.path("title").asText("");
JsonNode clues = catNode.get("clues");
if (title.isBlank() || clues == null || !clues.isArray()) {
continue;
}
TechtacularCategory category =
new TechtacularCategory(uniqueSlug(title, usedSlugs), trim(title, 200), order, true);
for (JsonNode clue : clues) {
String clueText = clue.path("clue").asText("");
String solution = clue.path("solution").asText("");
JsonNode distractors = clue.get("distractors");
if (clueText.isBlank() || solution.isBlank() || distractors == null || !distractors.isArray()) {
continue;
}
int points = clue.path("points").asInt(100);
String explanation = clue.hasNonNull("explanation") ? clue.get("explanation").asText() : null;
TechtacularQuestion question = new TechtacularQuestion(
trim(clueText, 1000),
(explanation == null || explanation.isBlank()) ? null : trim(explanation, 1000),
points);
int sort = 0;
question.addAnswer(new TechtacularAnswer(trim(solution, 500), true, sort++)); // richtige Antwort
for (JsonNode d : distractors) {
String dt = d.asText("");
if (!dt.isBlank()) {
question.addAnswer(new TechtacularAnswer(trim(dt, 500), false, sort++));
}
}
if (question.getAnswers().size() >= 2) {
category.addQuestion(question);
clueCount++;
}
}
if (!category.getQuestions().isEmpty()) {
categoryRepository.save(category);
order++;
catCount++;
}
}
System.out.println("✅ TechTacular: " + catCount + " Kategorien / " + clueCount + " Hinweise geladen.");
} catch (Exception e) {
System.out.println("⚠️ TechTacular-Seed übersprungen: " + e.getMessage());
}
}
private String uniqueSlug(String title, Set<String> used) {
String base = title.toLowerCase()
.replace("ä", "ae").replace("ö", "oe").replace("ü", "ue").replace("ß", "ss")
.replaceAll("[^a-z0-9]+", "-")
.replaceAll("(^-|-$)", "");
if (base.isBlank()) {
base = "kategorie";
}
String slug = base;
int counter = 2;
while (used.contains(slug) || categoryRepository.existsBySlug(slug)) {
slug = base + "-" + counter++;
}
used.add(slug);
return slug;
}
private String trim(String value, int max) {
if (value == null) {
return null;
}
return value.length() <= max ? value : value.substring(0, max);
}
}
@@ -0,0 +1,16 @@
package com.example.mindflux.config;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
@Configuration
public class WebConfig implements WebMvcConfigurer {
@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry
.addResourceHandler("/uploads/**")
.addResourceLocations("file:" + System.getProperty("user.dir") + "/uploads/");
}
}
@@ -0,0 +1,38 @@
package com.example.mindflux.controller;
import com.example.mindflux.model.Achievement;
import com.example.mindflux.service.AchievementService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import java.security.Principal;
import java.util.List;
@Controller
public class AchievementController {
@Autowired
private AchievementService achievementService;
@GetMapping("/profile/achievements")
public String showAchievements(Model model, Principal principal) {
String username = principal.getName();
List<Achievement> achievements = achievementService.getAchievementsForUser(username);
// 🔥 Dummy-Daten nur für Tests!
if (achievements == null || achievements.isEmpty()) {
achievements = List.of(
new Achievement("Hangman Hero", "Gewinne 10 Runden Hangman", "hangman.png", true),
new Achievement("Memory Meister", "Erreiche 1000 Punkte im Memory", "memory.png", false),
new Achievement("Quizkönig", "Beantworte 50 Fragen richtig", "quiz.png", true),
new Achievement("Early Bird", "Lerne vor 7 Uhr morgens", "earlybird.png", false)
);
}
model.addAttribute("achievements", achievements);
return "achievements"; // lädt achievements.html
}
}
@@ -0,0 +1,59 @@
package com.example.mindflux.controller;
import com.example.mindflux.service.MindMatchService;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
/**
* Admin-Verwaltung der MindMatch-Decks und -Paare. Liegt unter /admin/** und ist
* damit per SecurityConfig auf ROLE_ADMIN beschränkt.
*/
@Controller
@RequestMapping("/admin/mindmatch")
public class AdminMindMatchController {
private final MindMatchService mindMatchService;
public AdminMindMatchController(MindMatchService mindMatchService) {
this.mindMatchService = mindMatchService;
}
@GetMapping("")
public String manage(Model model) {
model.addAttribute("decks", mindMatchService.allDecksWithPairs());
return "admin/mindmatch";
}
@PostMapping("/decks")
public String createDeck(@RequestParam String title) {
mindMatchService.createDeck(title);
return "redirect:/admin/mindmatch";
}
@PostMapping("/decks/{deckId}/pairs")
public String addPair(@PathVariable Long deckId,
@RequestParam String term,
@RequestParam String match) {
mindMatchService.addPair(deckId, term, match);
return "redirect:/admin/mindmatch";
}
@PostMapping("/pairs/{pairId}/delete")
public String deletePair(@PathVariable Long pairId) {
mindMatchService.deletePair(pairId);
return "redirect:/admin/mindmatch";
}
@PostMapping("/decks/{deckId}/delete")
public String deleteDeck(@PathVariable Long deckId) {
mindMatchService.deleteDeck(deckId);
return "redirect:/admin/mindmatch";
}
@PostMapping("/decks/{deckId}/toggle")
public String toggleDeck(@PathVariable Long deckId) {
mindMatchService.toggleDeck(deckId);
return "redirect:/admin/mindmatch";
}
}
@@ -0,0 +1,79 @@
package com.example.mindflux.controller;
import com.example.mindflux.model.TechtacularCategory;
import com.example.mindflux.service.TechtacularService;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
import java.util.Arrays;
import java.util.List;
/** Admin-Verwaltung der TechTacular-Kategorien, -Fragen und -Antworten (ROLE_ADMIN via /admin/**). */
@Controller
@RequestMapping("/admin/techtacular")
public class AdminTechtacularController {
private final TechtacularService techtacularService;
public AdminTechtacularController(TechtacularService techtacularService) {
this.techtacularService = techtacularService;
}
/** Übersicht aller Kategorien. */
@GetMapping("")
public String manage(Model model) {
model.addAttribute("categories", techtacularService.categoryRows());
return "admin/techtacular";
}
/** Detailseite einer Kategorie mit ihren Fragen. */
@GetMapping("/categories/{categoryId}")
public String category(@PathVariable Long categoryId, Model model) {
TechtacularCategory category = techtacularService.categoryWithQuestions(categoryId);
if (category == null) {
return "redirect:/admin/techtacular";
}
model.addAttribute("category", category);
return "admin/techtacular-category";
}
@PostMapping("/categories")
public String createCategory(@RequestParam String title) {
techtacularService.createCategory(title);
return "redirect:/admin/techtacular";
}
@PostMapping("/categories/{categoryId}/questions")
public String addQuestion(@PathVariable Long categoryId,
@RequestParam String text,
@RequestParam(required = false) String explanation,
@RequestParam(defaultValue = "100") int points,
@RequestParam(required = false, defaultValue = "") String answer1,
@RequestParam(required = false, defaultValue = "") String answer2,
@RequestParam(required = false, defaultValue = "") String answer3,
@RequestParam(required = false, defaultValue = "") String answer4,
@RequestParam(defaultValue = "0") int correct) {
List<String> answers = Arrays.asList(answer1, answer2, answer3, answer4);
techtacularService.addQuestion(categoryId, text, explanation, points, answers, correct);
return "redirect:/admin/techtacular/categories/" + categoryId;
}
@PostMapping("/questions/{questionId}/delete")
public String deleteQuestion(@PathVariable Long questionId, @RequestParam Long categoryId) {
techtacularService.deleteQuestion(questionId);
return "redirect:/admin/techtacular/categories/" + categoryId;
}
@PostMapping("/categories/{categoryId}/delete")
public String deleteCategory(@PathVariable Long categoryId) {
techtacularService.deleteCategory(categoryId);
return "redirect:/admin/techtacular";
}
@PostMapping("/categories/{categoryId}/toggle")
public String toggleCategory(@PathVariable Long categoryId) {
techtacularService.toggleCategory(categoryId);
return "redirect:/admin/techtacular";
}
}
@@ -0,0 +1,66 @@
package com.example.mindflux.controller;
import com.example.mindflux.model.User;
import com.example.mindflux.service.AdminUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
@Controller
@RequestMapping("/admin")
public class AdminUserController {
@Autowired
private AdminUserService userService;
@Autowired
private PasswordEncoder passwordEncoder;
// ⬅️ Neu: Dashboard-Startseite
@GetMapping("")
public String adminDashboard() {
return "admin/dashboard"; // du brauchst: templates/admin/dashboard.html
}
// ⬅️ Benutzerverwaltung
@GetMapping("/users")
public String listUsers(Model model) {
model.addAttribute("users", userService.findAll());
return "admin/users/list";
}
@GetMapping("/users/new")
public String createUserForm(Model model) {
model.addAttribute("user", new User());
return "admin/users/form";
}
@PostMapping("/users/save")
public String saveUser(@ModelAttribute("user") User user) {
if (user.getId() != null && (user.getPassword() == null || user.getPassword().isBlank())) {
User existingUser = userService.findById(user.getId())
.orElseThrow(() -> new IllegalArgumentException("Ungültige User-ID: " + user.getId()));
user.setPassword(existingUser.getPassword());
} else {
user.setPassword(passwordEncoder.encode(user.getPassword()));
}
userService.save(user);
return "redirect:/admin/users";
}
@GetMapping("/users/edit/{id}")
public String editUserForm(@PathVariable Long id, Model model) {
User user = userService.findById(id).orElseThrow(() -> new IllegalArgumentException("Ungültige User-ID: " + id));
model.addAttribute("user", user);
return "admin/users/form";
}
@PostMapping("/users/delete/{id}")
public String deleteUser(@PathVariable Long id) {
userService.deleteById(id);
return "redirect:/admin/users";
}
}
@@ -0,0 +1,13 @@
package com.example.mindflux.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class DashboardController {
@GetMapping("/dashboard")
public String showDashboard() {
return "dashboard"; // lädt dashboard.html aus templates
}
}
@@ -0,0 +1,13 @@
package com.example.mindflux.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class DummyController {
@GetMapping("/comingsoon")
public String comingSoon() {
return "dummy"; // verweist auf dummy.html in src/main/resources/templates
}
}
@@ -0,0 +1,13 @@
package com.example.mindflux.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class FinalfluxController {
@GetMapping("/finalflux")
public String showFinalfluxOverview() {
return "finalflux"; // Lädt templates/finalflux.html
}
}
@@ -0,0 +1,50 @@
package com.example.mindflux.controller;
import com.example.mindflux.dto.GameStats;
import com.example.mindflux.dto.ScoreResult;
import com.example.mindflux.dto.ScoreSubmission;
import com.example.mindflux.service.GameScoreService;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import java.security.Principal;
import java.util.Set;
/**
* Generisches Score-API für alle Mindflux-Spiele. Der Spielname kommt aus der URL
* und wird gegen eine Allowlist geprüft, damit keine beliebigen Spiele-Kennungen
* in die Datenbank wandern.
*/
@RestController
@RequestMapping("/api/games")
public class GameScoreController {
/** Bekannte Spiele (entsprechen den Dashboard-Routen). */
private static final Set<String> KNOWN_GAMES = Set.of(
"mindmatch", "techtacular", "syntax-saga", "escape-room",
"service-clash", "bug-hunter", "netzwerker");
private final GameScoreService gameScoreService;
public GameScoreController(GameScoreService gameScoreService) {
this.gameScoreService = gameScoreService;
}
@PostMapping("/{game}/scores")
public ResponseEntity<ScoreResult> submitScore(@PathVariable String game,
@RequestBody ScoreSubmission submission,
Principal principal) {
if (!KNOWN_GAMES.contains(game)) {
return ResponseEntity.notFound().build();
}
return ResponseEntity.ok(gameScoreService.record(principal.getName(), game, submission));
}
@GetMapping("/{game}/stats")
public ResponseEntity<GameStats> getStats(@PathVariable String game, Principal principal) {
if (!KNOWN_GAMES.contains(game)) {
return ResponseEntity.notFound().build();
}
return ResponseEntity.ok(gameScoreService.getStats(principal.getName(), game));
}
}
@@ -0,0 +1,26 @@
package com.example.mindflux.controller;
import com.example.mindflux.dto.MindMatchDeckView;
import com.example.mindflux.service.MindMatchService;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
/** Liefert die aktiven MindMatch-Decks (inkl. Paare) an die Spielseite. */
@RestController
@RequestMapping("/api/mindmatch")
public class MindMatchApiController {
private final MindMatchService mindMatchService;
public MindMatchApiController(MindMatchService mindMatchService) {
this.mindMatchService = mindMatchService;
}
@GetMapping("/decks")
public List<MindMatchDeckView> decks() {
return mindMatchService.activeDecks();
}
}
@@ -0,0 +1,13 @@
package com.example.mindflux.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class MindMatchController {
@GetMapping("/mindmatch")
public String showMindMatch() {
return "mindmatch"; // lädt templates/mindmatch.html
}
}
@@ -0,0 +1,172 @@
package com.example.mindflux.controller;
import com.example.mindflux.model.User;
import com.example.mindflux.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.Authentication;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.web.authentication.logout.SecurityContextLogoutHandler;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.security.Principal;
import java.util.UUID;
@Controller
public class ProfileController {
@Autowired
private UserService userService;
@Autowired
private BCryptPasswordEncoder passwordEncoder;
private static final String UPLOAD_DIR = System.getProperty("user.dir") + "/uploads/profiles/";
@GetMapping("/profile")
public String profile(Model model, Principal principal, @RequestParam(value = "success", required = false) Boolean success) {
String username = principal.getName();
User user = userService.findByUsername(username);
model.addAttribute("user", user);
if (Boolean.TRUE.equals(success)) {
model.addAttribute("message", "Profil erfolgreich aktualisiert!");
}
return "profile";
}
@PostMapping("/profile/delete-picture")
public String deleteProfilePicture(Principal principal) {
String username = principal.getName();
User existingUser = userService.findByUsername(username);
if (existingUser != null) {
String profilePicture = existingUser.getProfilePicture();
if (profilePicture != null && !profilePicture.trim().isEmpty()) {
try {
Path picturePath = Paths.get(System.getProperty("user.dir"), "uploads", "profiles", profilePicture);
System.out.println("Versuche zu löschen: " + picturePath.toAbsolutePath());
if (Files.exists(picturePath)) {
Files.delete(picturePath);
System.out.println("Datei erfolgreich gelöscht: " + picturePath.getFileName());
} else {
System.out.println("Datei existiert nicht: " + picturePath.toAbsolutePath());
}
} catch (IOException e) {
System.err.println("Fehler beim Löschen der Datei: " + e.getMessage());
}
} else {
System.out.println("Kein Profilbild gesetzt, nichts zu löschen.");
}
existingUser.setProfilePicture(null); // Wichtig: auch wenn Datei nicht existiert
userService.save(existingUser);
}
return "redirect:/profile?success=true";
}
@GetMapping("/profile/knowledge")
public String knowledgeCenter(Model model, Principal principal) {
String username = principal.getName();
User user = userService.findByUsername(username);
model.addAttribute("user", user);
return "knowledge";
}
@PostMapping("/profile/update")
public String updateProfile(@RequestParam("email") String email,
@RequestParam(value = "profilePicture", required = false) MultipartFile file,
Principal principal) {
String username = principal.getName();
User existingUser = userService.findByUsername(username);
if (existingUser != null) {
existingUser.setEmail(email); // Email aktualisieren
if (file != null && !file.isEmpty()) {
try {
// Altes Profilbild löschen (falls vorhanden)
if (existingUser.getProfilePicture() != null && !existingUser.getProfilePicture().isEmpty()) {
Path oldFilePath = Paths.get(System.getProperty("user.dir"), "uploads", "profiles", existingUser.getProfilePicture());
if (Files.exists(oldFilePath)) {
Files.delete(oldFilePath);
}
}
// Neues Profilbild speichern
String fileExtension = getFileExtension(file.getOriginalFilename());
String fileName = UUID.randomUUID() + fileExtension;
Path uploadPath = Paths.get(UPLOAD_DIR);
Files.createDirectories(uploadPath);
Path filePath = uploadPath.resolve(fileName);
file.transferTo(filePath.toFile());
existingUser.setProfilePicture(fileName);
} catch (IOException e) {
e.printStackTrace();
}
}
userService.save(existingUser);
}
return "redirect:/profile?success=true";
}
@PostMapping("/profile/change-password")
public String changePassword(@RequestParam("oldPassword") String oldPassword,
@RequestParam("newPassword") String newPassword,
Principal principal,
Model model) {
String username = principal.getName();
User user = userService.findByUsername(username);
if (user == null) {
model.addAttribute("error", "Benutzer nicht gefunden.");
return "profile";
}
if (!passwordEncoder.matches(oldPassword, user.getPassword())) {
model.addAttribute("error", "Das aktuelle Passwort ist falsch.");
return "profile";
}
user.setPassword(passwordEncoder.encode(newPassword));
userService.save(user);
model.addAttribute("message", "Passwort erfolgreich geändert.");
return "profile";
}
@PostMapping("/profile/delete")
public String deleteProfile(Principal principal, Authentication authentication, HttpServletRequest request, HttpServletResponse response) {
String username = principal.getName();
userService.deleteByUsername(username);
new SecurityContextLogoutHandler().logout(request, response, authentication);
return "redirect:/?logout";
}
// Hilfsmethode: Dateiendung extrahieren
private String getFileExtension(String filename) {
if (filename == null || filename.lastIndexOf(".") == -1) {
return "";
}
return filename.substring(filename.lastIndexOf("."));
}
}
@@ -0,0 +1,47 @@
package com.example.mindflux.controller;
import com.example.mindflux.dto.GameProgress;
import com.example.mindflux.dto.ProgressData;
import com.example.mindflux.service.ProgressService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import java.security.Principal;
import java.util.List;
@Controller
public class ProgressController {
@Autowired
private ProgressService progressService;
@GetMapping("/progress") // <-- hier geändert!
public String showProgress(Model model, Principal principal) {
String username = principal.getName(); // aktueller eingeloggter Benutzer
ProgressData progress = progressService.getOverallProgress(username);
List<GameProgress> games = progressService.getGameProgress(username);
if (progress == null) {
// Falls keine Fortschrittsdaten vorhanden sind, Dummy-Daten setzen
model.addAttribute("correctAnswers", 0);
model.addAttribute("currentXp", 0);
model.addAttribute("xpForNextLevel", 1000);
model.addAttribute("userLevel", 1);
model.addAttribute("xpPercentage", 0);
} else {
model.addAttribute("correctAnswers", progress.getCorrectAnswers());
model.addAttribute("currentXp", progress.getCurrentXp());
model.addAttribute("xpForNextLevel", progress.getXpForNextLevel());
model.addAttribute("userLevel", progress.getUserLevel());
model.addAttribute("xpPercentage", progress.getProgressPercent());
}
model.addAttribute("gameProgress", games != null ? games : List.of()); // leere Liste, falls null
return "progress"; // ruft progress.html auf
}
}
@@ -0,0 +1,44 @@
package com.example.mindflux.controller;
import com.example.mindflux.model.User;
import com.example.mindflux.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
@Controller
public class RegisterController {
@Autowired
private UserService userService;
@Autowired
private PasswordEncoder passwordEncoder;
@GetMapping("/register")
public String showRegistrationForm(Model model) {
model.addAttribute("user", new User());
return "register";
}
@PostMapping("/register")
public String processRegistration(@ModelAttribute("user") User user, Model model) {
// Benutzername klein schreiben, um Doppelungen zu vermeiden
user.setUsername(user.getUsername().toLowerCase());
// Prüfen, ob Benutzername schon existiert
if (userService.findByUsername(user.getUsername()) != null) {
model.addAttribute("error", "Benutzername bereits vergeben.");
return "register";
}
// Passwort verschlüsseln
user.setPassword(passwordEncoder.encode(user.getPassword()));
user.setRole("USER"); // Standardrolle
userService.save(user);
return "redirect:/?registerSuccess"; // zurück zum Login mit Erfolgsmeldung
}
}
@@ -0,0 +1,13 @@
package com.example.mindflux.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class SettingsController {
@GetMapping("/profile/settings")
public String showSettingsPage() {
return "settings"; // lädt templates/settings.html
}
}
@@ -0,0 +1,13 @@
package com.example.mindflux.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class SozialesController {
@GetMapping("/soziales")
public String soziales() {
return "soziales"; // -> templates/soziales.html
}
}
@@ -0,0 +1,51 @@
package com.example.mindflux.controller;
import com.example.mindflux.dto.*;
import com.example.mindflux.service.TechtacularService;
import org.springframework.web.bind.annotation.*;
import java.security.Principal;
import java.util.HashSet;
import java.util.Set;
/** Spieler-API für TechTacular: Board laden, Antwort prüfen, Runde abschließen. */
@RestController
@RequestMapping("/api/techtacular")
public class TechtacularApiController {
private final TechtacularService techtacularService;
public TechtacularApiController(TechtacularService techtacularService) {
this.techtacularService = techtacularService;
}
/** exclude = komma-separierte Frage-IDs der Vorrunde, die möglichst nicht erneut kommen sollen. */
@GetMapping("/board")
public TechtacularBoardView board(@RequestParam(required = false) String exclude) {
return techtacularService.buildBoard(parseIds(exclude));
}
private Set<Long> parseIds(String csv) {
Set<Long> ids = new HashSet<>();
if (csv != null && !csv.isBlank()) {
for (String part : csv.split(",")) {
try {
ids.add(Long.parseLong(part.trim()));
} catch (NumberFormatException ignored) {
// ungültige IDs einfach überspringen
}
}
}
return ids;
}
@PostMapping("/answer")
public AnswerResult answer(@RequestBody AnswerRequest request) {
return techtacularService.checkAnswer(request.getQuestionId(), request.getAnswerId());
}
@PostMapping("/finish")
public TechtacularResult finish(@RequestBody FinishRequest request, Principal principal) {
return techtacularService.finish(principal.getName(), request);
}
}
@@ -0,0 +1,13 @@
package com.example.mindflux.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class TechtacularController {
@GetMapping("/techtacular")
public String showTechtacular() {
return "techtacular"; // lädt templates/techtacular.html
}
}
@@ -0,0 +1,67 @@
package com.example.mindflux.controller;
import com.example.mindflux.model.User;
import com.example.mindflux.repository.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.ResponseEntity;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.web.bind.annotation.*;
import java.util.List;
import java.util.Optional;
@RestController
@RequestMapping("/api/users")
public class UserController {
@Autowired
private UserRepository userRepository;
@Autowired
private PasswordEncoder passwordEncoder;
// 📥 User erstellen
@PostMapping
public User createUser(@RequestBody User user) {
user.setPassword(passwordEncoder.encode(user.getPassword()));
return userRepository.save(user);
}
// 📋 Alle User anzeigen
@GetMapping
public List<User> getAllUsers() {
return userRepository.findAll();
}
// 📍 Einzelnen User anzeigen
@GetMapping("/{id}")
public ResponseEntity<User> getUserById(@PathVariable Long id) {
Optional<User> user = userRepository.findById(id);
return user.map(ResponseEntity::ok)
.orElseGet(() -> ResponseEntity.notFound().build());
}
// ✏️ User aktualisieren
@PutMapping("/{id}")
public ResponseEntity<User> updateUser(@PathVariable Long id, @RequestBody User updatedUser) {
return userRepository.findById(id).map(user -> {
user.setUsername(updatedUser.getUsername());
if (updatedUser.getPassword() != null && !updatedUser.getPassword().isBlank()) {
user.setPassword(passwordEncoder.encode(updatedUser.getPassword()));
}
user.setEmail(updatedUser.getEmail());
user.setRole(updatedUser.getRole());
return ResponseEntity.ok(userRepository.save(user));
}).orElseGet(() -> ResponseEntity.notFound().build());
}
// 🗑️ User löschen
@DeleteMapping("/{id}")
public ResponseEntity<Void> deleteUser(@PathVariable Long id) {
if (userRepository.existsById(id)) {
userRepository.deleteById(id);
return ResponseEntity.noContent().build();
}
return ResponseEntity.notFound().build();
}
}
@@ -0,0 +1,31 @@
package com.example.mindflux.controller;
import com.example.mindflux.model.User;
import com.example.mindflux.repository.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
@Controller
@RequestMapping("/users")
public class UserViewController {
@Autowired
private UserRepository userRepository;
// Formular anzeigen
@GetMapping("/form")
public String showForm(Model model) {
model.addAttribute("user", new User());
return "user-form";
}
// Benutzer speichern
@PostMapping("/save")
public String saveUser(@ModelAttribute User user) {
userRepository.save(user);
return "user-success"; // statt redirect
}
}
@@ -0,0 +1,24 @@
package com.example.mindflux.dto;
/** Eine Zeile in der TechTacular-Kategorienübersicht (ohne alle Fragen zu laden). */
public class AdminCategoryRow {
private final Long id;
private final String slug;
private final String title;
private final boolean active;
private final long questionCount;
public AdminCategoryRow(Long id, String slug, String title, boolean active, long questionCount) {
this.id = id;
this.slug = slug;
this.title = title;
this.active = active;
this.questionCount = questionCount;
}
public Long getId() { return id; }
public String getSlug() { return slug; }
public String getTitle() { return title; }
public boolean isActive() { return active; }
public long getQuestionCount() { return questionCount; }
}
@@ -0,0 +1,13 @@
package com.example.mindflux.dto;
/** Eine vom Spieler gewählte Antwort. */
public class AnswerRequest {
private Long questionId;
private Long answerId;
public Long getQuestionId() { return questionId; }
public void setQuestionId(Long questionId) { this.questionId = questionId; }
public Long getAnswerId() { return answerId; }
public void setAnswerId(Long answerId) { this.answerId = answerId; }
}
@@ -0,0 +1,21 @@
package com.example.mindflux.dto;
/** Serverseitige Bewertung einer einzelnen Antwort (instant feedback). */
public class AnswerResult {
private final boolean correct;
private final Long correctAnswerId;
private final String explanation;
private final int points;
public AnswerResult(boolean correct, Long correctAnswerId, String explanation, int points) {
this.correct = correct;
this.correctAnswerId = correctAnswerId;
this.explanation = explanation;
this.points = points;
}
public boolean isCorrect() { return correct; }
public Long getCorrectAnswerId() { return correctAnswerId; }
public String getExplanation() { return explanation; }
public int getPoints() { return points; }
}
@@ -0,0 +1,15 @@
package com.example.mindflux.dto;
import java.util.List;
/** Abschluss einer TechTacular-Runde: alle gewählten Antworten + Dauer. Score wird serverseitig recomputed. */
public class FinishRequest {
private int durationSeconds;
private List<AnswerRequest> answers;
public int getDurationSeconds() { return durationSeconds; }
public void setDurationSeconds(int durationSeconds) { this.durationSeconds = durationSeconds; }
public List<AnswerRequest> getAnswers() { return answers; }
public void setAnswers(List<AnswerRequest> answers) { this.answers = answers; }
}
@@ -0,0 +1,25 @@
package com.example.mindflux.dto;
import java.time.LocalDate;
public class GameProgress {
private String name;
private int progressPercent;
private int highscore;
private int plays;
private LocalDate lastPlayed;
// Getter
public String getName() { return name; }
public int getProgressPercent() { return progressPercent; }
public int getHighscore() { return highscore; }
public int getPlays() { return plays; }
public LocalDate getLastPlayed() { return lastPlayed; }
// Setter
public void setName(String name) { this.name = name; }
public void setProgressPercent(int progressPercent) { this.progressPercent = progressPercent; }
public void setHighscore(int highscore) { this.highscore = highscore; }
public void setPlays(int plays) { this.plays = plays; }
public void setLastPlayed(LocalDate lastPlayed) { this.lastPlayed = lastPlayed; }
}
@@ -0,0 +1,20 @@
package com.example.mindflux.dto;
import java.time.LocalDate;
/** Zusammengefasste Statistik eines Spielers für ein Spiel. */
public class GameStats {
private final int highscore;
private final long plays;
private final LocalDate lastPlayed;
public GameStats(int highscore, long plays, LocalDate lastPlayed) {
this.highscore = highscore;
this.plays = plays;
this.lastPlayed = lastPlayed;
}
public int getHighscore() { return highscore; }
public long getPlays() { return plays; }
public LocalDate getLastPlayed() { return lastPlayed; }
}
@@ -0,0 +1,20 @@
package com.example.mindflux.dto;
import java.util.List;
/** Ein aktives Deck mit seinen Paaren fürs Spiel-API. */
public class MindMatchDeckView {
private final String slug;
private final String title;
private final List<MindMatchPairView> pairs;
public MindMatchDeckView(String slug, String title, List<MindMatchPairView> pairs) {
this.slug = slug;
this.title = title;
this.pairs = pairs;
}
public String getSlug() { return slug; }
public String getTitle() { return title; }
public List<MindMatchPairView> getPairs() { return pairs; }
}
@@ -0,0 +1,15 @@
package com.example.mindflux.dto;
/** Ein Paar fürs Spiel-API. Feld heißt "match" (passend zur bisherigen JS-Logik). */
public class MindMatchPairView {
private final String term;
private final String match;
public MindMatchPairView(String term, String match) {
this.term = term;
this.match = match;
}
public String getTerm() { return term; }
public String getMatch() { return match; }
}
@@ -0,0 +1,49 @@
package com.example.mindflux.dto;
public class ProgressData {
private int correctAnswers;
private int currentXp;
private int xpForNextLevel;
private int userLevel;
private int progressPercent;
public int getCorrectAnswers() {
return correctAnswers;
}
public void setCorrectAnswers(int correctAnswers) {
this.correctAnswers = correctAnswers;
}
public int getCurrentXp() {
return currentXp;
}
public void setCurrentXp(int currentXp) {
this.currentXp = currentXp;
}
public int getXpForNextLevel() {
return xpForNextLevel;
}
public void setXpForNextLevel(int xpForNextLevel) {
this.xpForNextLevel = xpForNextLevel;
}
public int getUserLevel() {
return userLevel;
}
public void setUserLevel(int userLevel) {
this.userLevel = userLevel;
}
public int getProgressPercent() {
return progressPercent;
}
public void setProgressPercent(int progressPercent) {
this.progressPercent = progressPercent;
}
}
@@ -0,0 +1,21 @@
package com.example.mindflux.dto;
/** Antwort nach dem Speichern eines Ergebnisses. */
public class ScoreResult {
private final int score;
private final int highscore;
private final boolean newHighscore;
private final long plays;
public ScoreResult(int score, int highscore, boolean newHighscore, long plays) {
this.score = score;
this.highscore = highscore;
this.newHighscore = newHighscore;
this.plays = plays;
}
public int getScore() { return score; }
public int getHighscore() { return highscore; }
public boolean isNewHighscore() { return newHighscore; }
public long getPlays() { return plays; }
}
@@ -0,0 +1,25 @@
package com.example.mindflux.dto;
/**
* Was der Client nach einem abgeschlossenen Spiel sendet. Der Score wird
* bewusst NICHT mitgeschickt, sondern serverseitig aus diesen Rohwerten
* berechnet, damit ein manipulierter Client keinen Fantasie-Score speichern kann.
*/
public class ScoreSubmission {
private String deck;
private int pairs;
private int moves;
private int durationSeconds;
public String getDeck() { return deck; }
public void setDeck(String deck) { this.deck = deck; }
public int getPairs() { return pairs; }
public void setPairs(int pairs) { this.pairs = pairs; }
public int getMoves() { return moves; }
public void setMoves(int moves) { this.moves = moves; }
public int getDurationSeconds() { return durationSeconds; }
public void setDurationSeconds(int durationSeconds) { this.durationSeconds = durationSeconds; }
}
@@ -0,0 +1,66 @@
package com.example.mindflux.dto;
import java.util.List;
/**
* Das Jeopardy-Board fürs Frontend: Spalten (Kategorien) mit Kacheln (Fragen).
* Bewusst OHNE Information darüber, welche Antwort korrekt ist – geprüft wird serverseitig.
*/
public class TechtacularBoardView {
private final List<Category> categories;
private final int maxScore;
public TechtacularBoardView(List<Category> categories, int maxScore) {
this.categories = categories;
this.maxScore = maxScore;
}
public List<Category> getCategories() { return categories; }
public int getMaxScore() { return maxScore; }
public static class Category {
private final String title;
private final List<Tile> tiles;
public Category(String title, List<Tile> tiles) {
this.title = title;
this.tiles = tiles;
}
public String getTitle() { return title; }
public List<Tile> getTiles() { return tiles; }
}
public static class Tile {
private final Long questionId;
private final int points;
private final String text;
private final List<Option> answers;
public Tile(Long questionId, int points, String text, List<Option> answers) {
this.questionId = questionId;
this.points = points;
this.text = text;
this.answers = answers;
}
public Long getQuestionId() { return questionId; }
public int getPoints() { return points; }
public String getText() { return text; }
public List<Option> getAnswers() { return answers; }
}
public static class Option {
private final Long id;
private final String text;
public Option(Long id, String text) {
this.id = id;
this.text = text;
}
public Long getId() { return id; }
public String getText() { return text; }
}
}
@@ -0,0 +1,31 @@
package com.example.mindflux.dto;
/** Ergebnis einer abgeschlossenen TechTacular-Runde. */
public class TechtacularResult {
private final int score;
private final int maxScore;
private final int correctCount;
private final int totalCount;
private final int highscore;
private final boolean newHighscore;
private final long plays;
public TechtacularResult(int score, int maxScore, int correctCount, int totalCount,
int highscore, boolean newHighscore, long plays) {
this.score = score;
this.maxScore = maxScore;
this.correctCount = correctCount;
this.totalCount = totalCount;
this.highscore = highscore;
this.newHighscore = newHighscore;
this.plays = plays;
}
public int getScore() { return score; }
public int getMaxScore() { return maxScore; }
public int getCorrectCount() { return correctCount; }
public int getTotalCount() { return totalCount; }
public int getHighscore() { return highscore; }
public boolean isNewHighscore() { return newHighscore; }
public long getPlays() { return plays; }
}
@@ -0,0 +1,51 @@
package com.example.mindflux.model;
import jakarta.persistence.*;
import java.time.LocalDateTime;
@Entity
@Table(name = "achievements")
public class Achievement {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String username;
private String title;
private String description;
private String icon; // Dateiname des Icons (z.B. "star.png")
private LocalDateTime dateAchieved;
// 🔥 Neuer Konstruktor für schnelle Dummy-Erstellung (ohne username/dateAchieved)
public Achievement(String title, String description, String icon, boolean unlocked) {
this.title = title;
this.description = description;
this.icon = icon;
this.dateAchieved = unlocked ? LocalDateTime.now() : null;
}
// ⚡ Standard-Konstruktor (wichtig für JPA!)
public Achievement() {
}
// Getter und Setter
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public String getUsername() { return username; }
public void setUsername(String username) { this.username = username; }
public String getTitle() { return title; }
public void setTitle(String title) { this.title = title; }
public String getDescription() { return description; }
public void setDescription(String description) { this.description = description; }
public String getIcon() { return icon; }
public void setIcon(String icon) { this.icon = icon; }
public LocalDateTime getDateAchieved() { return dateAchieved; }
public void setDateAchieved(LocalDateTime dateAchieved) { this.dateAchieved = dateAchieved; }
}
@@ -0,0 +1,75 @@
package com.example.mindflux.model;
import jakarta.persistence.*;
import java.time.LocalDateTime;
/**
* Ein einzelnes Spielergebnis. Bewusst generisch gehalten, damit alle
* Mindflux-Spiele (MindMatch, TechTacular, ...) dieselbe Tabelle nutzen können.
* Welches Spiel das Ergebnis erzeugt hat, steht in {@link #game}.
*/
@Entity
@Table(name = "game_scores")
public class GameScore {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String username;
/** Spiel-Kennung, z.B. "mindmatch" (entspricht der Route im Dashboard). */
private String game;
/** Optionales Deck / Level innerhalb des Spiels, z.B. "netzwerk". */
private String deck;
private int score;
/** Anzahl der Zug-Versuche (kann je nach Spiel null sein). */
private Integer moves;
@Column(name = "duration_seconds")
private Integer durationSeconds;
@Column(name = "played_at")
private LocalDateTime playedAt;
public GameScore() {
}
public GameScore(String username, String game, String deck, int score,
Integer moves, Integer durationSeconds, LocalDateTime playedAt) {
this.username = username;
this.game = game;
this.deck = deck;
this.score = score;
this.moves = moves;
this.durationSeconds = durationSeconds;
this.playedAt = playedAt;
}
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public String getUsername() { return username; }
public void setUsername(String username) { this.username = username; }
public String getGame() { return game; }
public void setGame(String game) { this.game = game; }
public String getDeck() { return deck; }
public void setDeck(String deck) { this.deck = deck; }
public int getScore() { return score; }
public void setScore(int score) { this.score = score; }
public Integer getMoves() { return moves; }
public void setMoves(Integer moves) { this.moves = moves; }
public Integer getDurationSeconds() { return durationSeconds; }
public void setDurationSeconds(Integer durationSeconds) { this.durationSeconds = durationSeconds; }
public LocalDateTime getPlayedAt() { return playedAt; }
public void setPlayedAt(LocalDateTime playedAt) { this.playedAt = playedAt; }
}
@@ -0,0 +1,63 @@
package com.example.mindflux.model;
import jakarta.persistence.*;
import java.util.ArrayList;
import java.util.List;
/** Ein MindMatch-Deck (Kategorie) mit seinen Begriffspaaren. Von Admins pflegbar. */
@Entity
@Table(name = "mindmatch_decks")
public class MindMatchDeck {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(unique = true)
private String slug;
private String title;
@Column(name = "sort_order")
private int sortOrder;
private boolean active = true;
@OneToMany(mappedBy = "deck", cascade = CascadeType.ALL, orphanRemoval = true)
@OrderBy("id ASC")
private List<MindMatchPair> pairs = new ArrayList<>();
public MindMatchDeck() {
}
public MindMatchDeck(String slug, String title, int sortOrder, boolean active) {
this.slug = slug;
this.title = title;
this.sortOrder = sortOrder;
this.active = active;
}
/** Fügt ein Paar hinzu und hält die Rückreferenz konsistent. */
public void addPair(MindMatchPair pair) {
pair.setDeck(this);
this.pairs.add(pair);
}
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public String getSlug() { return slug; }
public void setSlug(String slug) { this.slug = slug; }
public String getTitle() { return title; }
public void setTitle(String title) { this.title = title; }
public int getSortOrder() { return sortOrder; }
public void setSortOrder(int sortOrder) { this.sortOrder = sortOrder; }
public boolean isActive() { return active; }
public void setActive(boolean active) { this.active = active; }
public List<MindMatchPair> getPairs() { return pairs; }
public void setPairs(List<MindMatchPair> pairs) { this.pairs = pairs; }
}
@@ -0,0 +1,43 @@
package com.example.mindflux.model;
import jakarta.persistence.*;
/** Ein Begriffspaar innerhalb eines {@link MindMatchDeck}: Begriff + zugehörige Bedeutung. */
@Entity
@Table(name = "mindmatch_pairs")
public class MindMatchPair {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "deck_id")
private MindMatchDeck deck;
private String term;
/** Spalte heißt "match_text", da MATCH in SQL ein reserviertes Wort ist. */
@Column(name = "match_text")
private String matchText;
public MindMatchPair() {
}
public MindMatchPair(String term, String matchText) {
this.term = term;
this.matchText = matchText;
}
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public MindMatchDeck getDeck() { return deck; }
public void setDeck(MindMatchDeck deck) { this.deck = deck; }
public String getTerm() { return term; }
public void setTerm(String term) { this.term = term; }
public String getMatchText() { return matchText; }
public void setMatchText(String matchText) { this.matchText = matchText; }
}
@@ -0,0 +1,49 @@
package com.example.mindflux.model;
import jakarta.persistence.*;
/** Eine Antwortmöglichkeit zu einer {@link TechtacularQuestion}. */
@Entity
@Table(name = "techtacular_answers")
public class TechtacularAnswer {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "question_id")
private TechtacularQuestion question;
@Column(name = "answer_text")
private String text;
private boolean correct;
@Column(name = "sort_order")
private int sortOrder;
public TechtacularAnswer() {
}
public TechtacularAnswer(String text, boolean correct, int sortOrder) {
this.text = text;
this.correct = correct;
this.sortOrder = sortOrder;
}
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public TechtacularQuestion getQuestion() { return question; }
public void setQuestion(TechtacularQuestion question) { this.question = question; }
public String getText() { return text; }
public void setText(String text) { this.text = text; }
public boolean isCorrect() { return correct; }
public void setCorrect(boolean correct) { this.correct = correct; }
public int getSortOrder() { return sortOrder; }
public void setSortOrder(int sortOrder) { this.sortOrder = sortOrder; }
}
@@ -0,0 +1,62 @@
package com.example.mindflux.model;
import jakarta.persistence.*;
import java.util.ArrayList;
import java.util.List;
/** Eine TechTacular-Kategorie (Spalte im Jeopardy-Board) mit ihren Fragen. */
@Entity
@Table(name = "techtacular_categories")
public class TechtacularCategory {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(unique = true)
private String slug;
private String title;
@Column(name = "sort_order")
private int sortOrder;
private boolean active = true;
@OneToMany(mappedBy = "category", cascade = CascadeType.ALL, orphanRemoval = true)
@OrderBy("points ASC, id ASC")
private List<TechtacularQuestion> questions = new ArrayList<>();
public TechtacularCategory() {
}
public TechtacularCategory(String slug, String title, int sortOrder, boolean active) {
this.slug = slug;
this.title = title;
this.sortOrder = sortOrder;
this.active = active;
}
public void addQuestion(TechtacularQuestion question) {
question.setCategory(this);
this.questions.add(question);
}
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public String getSlug() { return slug; }
public void setSlug(String slug) { this.slug = slug; }
public String getTitle() { return title; }
public void setTitle(String title) { this.title = title; }
public int getSortOrder() { return sortOrder; }
public void setSortOrder(int sortOrder) { this.sortOrder = sortOrder; }
public boolean isActive() { return active; }
public void setActive(boolean active) { this.active = active; }
public List<TechtacularQuestion> getQuestions() { return questions; }
public void setQuestions(List<TechtacularQuestion> questions) { this.questions = questions; }
}
@@ -0,0 +1,67 @@
package com.example.mindflux.model;
import jakarta.persistence.*;
import java.util.ArrayList;
import java.util.List;
/** Eine Frage mit ihren Antwortmöglichkeiten (genau eine ist korrekt) und Punktwert. */
@Entity
@Table(name = "techtacular_questions")
public class TechtacularQuestion {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "category_id")
private TechtacularCategory category;
@Column(name = "question_text")
private String text;
private String explanation;
private int points;
@OneToMany(mappedBy = "question", cascade = CascadeType.ALL, orphanRemoval = true)
@OrderBy("sortOrder ASC, id ASC")
private List<TechtacularAnswer> answers = new ArrayList<>();
public TechtacularQuestion() {
}
public TechtacularQuestion(String text, String explanation, int points) {
this.text = text;
this.explanation = explanation;
this.points = points;
}
public void addAnswer(TechtacularAnswer answer) {
answer.setQuestion(this);
this.answers.add(answer);
}
/** Liefert die als korrekt markierte Antwort (oder null). */
public TechtacularAnswer correctAnswer() {
return answers.stream().filter(TechtacularAnswer::isCorrect).findFirst().orElse(null);
}
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public TechtacularCategory getCategory() { return category; }
public void setCategory(TechtacularCategory category) { this.category = category; }
public String getText() { return text; }
public void setText(String text) { this.text = text; }
public String getExplanation() { return explanation; }
public void setExplanation(String explanation) { this.explanation = explanation; }
public int getPoints() { return points; }
public void setPoints(int points) { this.points = points; }
public List<TechtacularAnswer> getAnswers() { return answers; }
public void setAnswers(List<TechtacularAnswer> answers) { this.answers = answers; }
}
@@ -0,0 +1,54 @@
package com.example.mindflux.model;
import com.fasterxml.jackson.annotation.JsonProperty;
import jakarta.persistence.*;
@Entity
@Table(name = "users")
public class User {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String username;
@JsonProperty(access = JsonProperty.Access.WRITE_ONLY)
private String password;
private String email;
private String role;
@Column(name = "profile_picture")
private String profilePicture;
public User() {}
public User(String username, String password, String email, String role) {
this.username = username;
this.password = password;
this.email = email;
this.role = role;
}
// —————————————
// Getter / Setter
// —————————————
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
public String getUsername() { return username; }
public void setUsername(String u) { this.username = u; }
public String getPassword() { return password; }
public void setPassword(String p) { this.password = p; }
public String getEmail() { return email; }
public void setEmail(String e) { this.email = e; }
public String getRole() { return role; }
public void setRole(String r) { this.role = r; }
public String getProfilePicture() { return profilePicture; }
public void setProfilePicture(String pictureUrl) { this.profilePicture = pictureUrl; }
}
@@ -0,0 +1,10 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.Achievement;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.List;
public interface AchievementRepository extends JpaRepository<Achievement, Long> {
List<Achievement> findByUsername(String username);
}
@@ -0,0 +1,7 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.User;
import org.springframework.data.jpa.repository.JpaRepository;
public interface AdminUserRepository extends JpaRepository<User, Long> {
}
@@ -0,0 +1,18 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.GameScore;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.Optional;
public interface GameScoreRepository extends JpaRepository<GameScore, Long> {
/** Bestes Ergebnis eines Spielers in einem Spiel (Highscore). */
Optional<GameScore> findTopByUsernameAndGameOrderByScoreDesc(String username, String game);
/** Zuletzt gespieltes Ergebnis eines Spielers in einem Spiel. */
Optional<GameScore> findTopByUsernameAndGameOrderByPlayedAtDesc(String username, String game);
/** Wie oft ein Spieler ein Spiel abgeschlossen hat. */
long countByUsernameAndGame(String username, String game);
}
@@ -0,0 +1,18 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.MindMatchDeck;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.List;
import java.util.Optional;
public interface MindMatchDeckRepository extends JpaRepository<MindMatchDeck, Long> {
List<MindMatchDeck> findAllByActiveTrueOrderBySortOrderAscIdAsc();
List<MindMatchDeck> findAllByOrderBySortOrderAscIdAsc();
Optional<MindMatchDeck> findBySlug(String slug);
boolean existsBySlug(String slug);
}
@@ -0,0 +1,7 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.MindMatchPair;
import org.springframework.data.jpa.repository.JpaRepository;
public interface MindMatchPairRepository extends JpaRepository<MindMatchPair, Long> {
}
@@ -0,0 +1,7 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.TechtacularAnswer;
import org.springframework.data.jpa.repository.JpaRepository;
public interface TechtacularAnswerRepository extends JpaRepository<TechtacularAnswer, Long> {
}
@@ -0,0 +1,15 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.TechtacularCategory;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.List;
public interface TechtacularCategoryRepository extends JpaRepository<TechtacularCategory, Long> {
List<TechtacularCategory> findAllByActiveTrueOrderBySortOrderAscIdAsc();
List<TechtacularCategory> findAllByOrderBySortOrderAscIdAsc();
boolean existsBySlug(String slug);
}
@@ -0,0 +1,9 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.TechtacularQuestion;
import org.springframework.data.jpa.repository.JpaRepository;
public interface TechtacularQuestionRepository extends JpaRepository<TechtacularQuestion, Long> {
long countByCategoryId(Long categoryId);
}
@@ -0,0 +1,14 @@
package com.example.mindflux.repository;
import com.example.mindflux.model.User;
import org.springframework.data.jpa.repository.JpaRepository;
import java.util.Optional;
public interface UserRepository extends JpaRepository<User, Long> {
// Benutzer anhand des Benutzernamens suchen
Optional<User> findByUsername(String username);
// Benutzer anhand des Benutzernamens löschen
void deleteByUsername(String username);
}
@@ -0,0 +1,9 @@
package com.example.mindflux.service;
import com.example.mindflux.model.Achievement;
import java.util.List;
public interface AchievementService {
List<Achievement> getAchievementsForUser(String username);
}
@@ -0,0 +1,20 @@
package com.example.mindflux.service;
import com.example.mindflux.model.Achievement;
import com.example.mindflux.repository.AchievementRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
@Service
public class AchievementServiceImpl implements AchievementService {
@Autowired
private AchievementRepository achievementRepository;
@Override
public List<Achievement> getAchievementsForUser(String username) {
return achievementRepository.findByUsername(username);
}
}
@@ -0,0 +1,32 @@
package com.example.mindflux.service;
import com.example.mindflux.model.User;
import com.example.mindflux.repository.AdminUserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
import java.util.Optional;
@Service
public class AdminUserService {
@Autowired
private AdminUserRepository userRepository;
public List<User> findAll() {
return userRepository.findAll();
}
public Optional<User> findById(Long id) {
return userRepository.findById(id);
}
public User save(User user) {
return userRepository.save(user);
}
public void deleteById(Long id) {
userRepository.deleteById(id);
}
}
@@ -0,0 +1,83 @@
package com.example.mindflux.service;
import com.example.mindflux.dto.GameStats;
import com.example.mindflux.dto.ScoreResult;
import com.example.mindflux.dto.ScoreSubmission;
import com.example.mindflux.model.GameScore;
import com.example.mindflux.repository.GameScoreRepository;
import org.springframework.stereotype.Service;
import java.time.LocalDateTime;
/**
* Speichert Spielergebnisse und liefert Statistiken. Der Score wird hier
* autoritativ berechnet – der Client schickt nur die Rohwerte.
*/
@Service
public class GameScoreService {
private final GameScoreRepository repository;
public GameScoreService(GameScoreRepository repository) {
this.repository = repository;
}
/**
* Punktezahl aus Genauigkeit und Tempo.
* <ul>
* <li>Genauigkeit: {@code 1000 * Paare / Züge} – 1000 Punkte bei perfektem Spiel
* (jeder Aufdeck-Versuch ein Treffer), weniger bei vielen Fehlversuchen.</li>
* <li>Zeitbonus: bis zu 500 Punkte, der nach 100 Sekunden auf 0 fällt.</li>
* </ul>
* Identisch in {@code mindmatch.js} gespiegelt, damit der Client sofort denselben
* Wert anzeigt.
*/
public static int calculateScore(int pairs, int moves, int durationSeconds) {
if (pairs <= 0) {
return 0;
}
int safeMoves = Math.max(moves, pairs); // niemals weniger Züge als Paare
int safeSeconds = Math.max(durationSeconds, 0);
int accuracyScore = Math.round(1000f * pairs / safeMoves);
int timeBonus = Math.max(0, 500 - safeSeconds * 5);
return accuracyScore + timeBonus;
}
/** Speichert ein abgeschlossenes MindMatch-Spiel (Score aus Rohwerten berechnet). */
public ScoreResult record(String username, String game, ScoreSubmission submission) {
int moves = Math.max(submission.getMoves(), submission.getPairs());
int seconds = Math.max(submission.getDurationSeconds(), 0);
int score = calculateScore(submission.getPairs(), moves, seconds);
return recordScore(username, game, submission.getDeck(), score, moves, seconds);
}
/** Speichert ein bereits berechnetes Ergebnis (z.B. TechTacular) und liefert den Highscore-Stand. */
public ScoreResult recordScore(String username, String game, String deck,
int score, Integer moves, Integer durationSeconds) {
GameScore previousBest = repository
.findTopByUsernameAndGameOrderByScoreDesc(username, game)
.orElse(null);
repository.save(new GameScore(
username, game, deck, score, moves, durationSeconds, LocalDateTime.now()));
boolean newHighscore = previousBest == null || score > previousBest.getScore();
int highscore = previousBest == null ? score : Math.max(previousBest.getScore(), score);
long plays = repository.countByUsernameAndGame(username, game);
return new ScoreResult(score, highscore, newHighscore, plays);
}
/** Aktuelle Statistik (Highscore, Anzahl Spiele, zuletzt gespielt) für ein Spiel. */
public GameStats getStats(String username, String game) {
int highscore = repository.findTopByUsernameAndGameOrderByScoreDesc(username, game)
.map(GameScore::getScore)
.orElse(0);
long plays = repository.countByUsernameAndGame(username, game);
var lastPlayed = repository.findTopByUsernameAndGameOrderByPlayedAtDesc(username, game)
.map(score -> score.getPlayedAt().toLocalDate())
.orElse(null);
return new GameStats(highscore, plays, lastPlayed);
}
}
@@ -0,0 +1,102 @@
package com.example.mindflux.service;
import com.example.mindflux.dto.MindMatchDeckView;
import com.example.mindflux.dto.MindMatchPairView;
import com.example.mindflux.model.MindMatchDeck;
import com.example.mindflux.model.MindMatchPair;
import com.example.mindflux.repository.MindMatchDeckRepository;
import com.example.mindflux.repository.MindMatchPairRepository;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.List;
@Service
public class MindMatchService {
private final MindMatchDeckRepository deckRepository;
private final MindMatchPairRepository pairRepository;
public MindMatchService(MindMatchDeckRepository deckRepository, MindMatchPairRepository pairRepository) {
this.deckRepository = deckRepository;
this.pairRepository = pairRepository;
}
// ---------- Spieler ----------
/** Aktive Decks mit Paaren fürs Spiel (open-in-view=false -> hier initialisiert). */
@Transactional(readOnly = true)
public List<MindMatchDeckView> activeDecks() {
return deckRepository.findAllByActiveTrueOrderBySortOrderAscIdAsc().stream()
.map(deck -> new MindMatchDeckView(
deck.getSlug(),
deck.getTitle(),
deck.getPairs().stream()
.map(pair -> new MindMatchPairView(pair.getTerm(), pair.getMatchText()))
.toList()))
.toList();
}
// ---------- Admin ----------
/** Alle Decks (auch inaktive) inkl. Paaren für die Verwaltung. */
@Transactional(readOnly = true)
public List<MindMatchDeck> allDecksWithPairs() {
List<MindMatchDeck> decks = deckRepository.findAllByOrderBySortOrderAscIdAsc();
decks.forEach(deck -> deck.getPairs().size()); // Lazy-Collection laden
return decks;
}
@Transactional
public void createDeck(String title) {
if (title == null || title.isBlank()) {
return;
}
String clean = title.trim();
int order = (int) deckRepository.count() + 1;
deckRepository.save(new MindMatchDeck(uniqueSlug(clean), clean, order, true));
}
@Transactional
public void addPair(Long deckId, String term, String match) {
if (term == null || term.isBlank() || match == null || match.isBlank()) {
return;
}
deckRepository.findById(deckId).ifPresent(deck -> {
deck.addPair(new MindMatchPair(term.trim(), match.trim()));
deckRepository.save(deck);
});
}
@Transactional
public void deletePair(Long pairId) {
pairRepository.deleteById(pairId);
}
@Transactional
public void deleteDeck(Long deckId) {
deckRepository.deleteById(deckId);
}
@Transactional
public void toggleDeck(Long deckId) {
deckRepository.findById(deckId).ifPresent(deck -> deck.setActive(!deck.isActive()));
}
/** Erzeugt aus dem Titel einen URL-tauglichen, eindeutigen Slug. */
private String uniqueSlug(String title) {
String base = title.toLowerCase()
.replace("ä", "ae").replace("ö", "oe").replace("ü", "ue").replace("ß", "ss")
.replaceAll("[^a-z0-9]+", "-")
.replaceAll("(^-|-$)", "");
if (base.isBlank()) {
base = "deck";
}
String slug = base;
int counter = 2;
while (deckRepository.existsBySlug(slug)) {
slug = base + "-" + counter++;
}
return slug;
}
}
@@ -0,0 +1,66 @@
package com.example.mindflux.service;
import com.example.mindflux.dto.GameProgress;
import com.example.mindflux.dto.GameStats;
import com.example.mindflux.dto.ProgressData;
import org.springframework.stereotype.Service;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
@Service
public class ProgressService {
/** Spiel-Kennung -> Anzeigename, in Dashboard-Reihenfolge. */
private static final Map<String, String> GAMES = new LinkedHashMap<>();
static {
GAMES.put("mindmatch", "MindMatch");
GAMES.put("techtacular", "TechTacular");
GAMES.put("syntax-saga", "Syntax Saga");
GAMES.put("escape-room", "Code Escape Room");
GAMES.put("service-clash", "Service Clash");
GAMES.put("bug-hunter", "Bug Hunter");
GAMES.put("netzwerker", "Netzwerker");
}
private final GameScoreService gameScoreService;
public ProgressService(GameScoreService gameScoreService) {
this.gameScoreService = gameScoreService;
}
public ProgressData getOverallProgress(String username) {
// Dummy-Daten – später aus DB berechnen
ProgressData data = new ProgressData();
data.setCorrectAnswers(432);
data.setCurrentXp(2400);
data.setXpForNextLevel(3000);
data.setUserLevel(5);
data.setProgressPercent(78);
return data;
}
/** Echter Spiel-Fortschritt pro Spiel aus der Datenbank (game_scores). */
public List<GameProgress> getGameProgress(String username) {
List<GameProgress> result = new ArrayList<>();
for (Map.Entry<String, String> entry : GAMES.entrySet()) {
GameStats stats = gameScoreService.getStats(username, entry.getKey());
result.add(toGameProgress(entry.getValue(), stats));
}
return result;
}
private GameProgress toGameProgress(String displayName, GameStats stats) {
GameProgress game = new GameProgress();
game.setName(displayName);
game.setHighscore(stats.getHighscore());
game.setPlays((int) stats.getPlays());
game.setLastPlayed(stats.getLastPlayed());
// Fortschritt auf der Score-Skala (max ~1500 Punkte -> 100 %).
game.setProgressPercent(Math.min(100, Math.round(stats.getHighscore() / 15.0f)));
return game;
}
}
@@ -0,0 +1,227 @@
package com.example.mindflux.service;
import com.example.mindflux.dto.*;
import com.example.mindflux.model.TechtacularAnswer;
import com.example.mindflux.model.TechtacularCategory;
import com.example.mindflux.model.TechtacularQuestion;
import com.example.mindflux.repository.TechtacularCategoryRepository;
import com.example.mindflux.repository.TechtacularQuestionRepository;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.*;
import java.util.stream.Collectors;
@Service
public class TechtacularService {
private static final String GAME = "techtacular";
private static final int BOARD_CATEGORIES = 5;
private static final int[] POINT_TIERS = {100, 200, 300, 400, 500};
private final TechtacularCategoryRepository categoryRepository;
private final TechtacularQuestionRepository questionRepository;
private final GameScoreService gameScoreService;
private final Random random = new Random();
public TechtacularService(TechtacularCategoryRepository categoryRepository,
TechtacularQuestionRepository questionRepository,
GameScoreService gameScoreService) {
this.categoryRepository = categoryRepository;
this.questionRepository = questionRepository;
this.gameScoreService = gameScoreService;
}
// ---------- Spieler ----------
/**
* Baut ein zufälliges Board: bis zu 5 Kategorien, je eine Frage pro Punktstufe (100–500).
* Fragen aus {@code exclude} (z.B. die Vorrunde) werden möglichst vermieden, damit jede
* Runde mit überwiegend neuen Fragen gefüllt wird.
*/
@Transactional(readOnly = true)
public TechtacularBoardView buildBoard(Set<Long> exclude) {
Set<Long> excluded = (exclude == null) ? Set.of() : exclude;
List<TechtacularCategory> usable = categoryRepository.findAllByActiveTrueOrderBySortOrderAscIdAsc()
.stream().filter(c -> !c.getQuestions().isEmpty()).collect(Collectors.toList());
Collections.shuffle(usable, random);
List<TechtacularCategory> chosen = usable.stream().limit(BOARD_CATEGORIES).toList();
List<TechtacularBoardView.Category> columns = new ArrayList<>();
int maxScore = 0;
for (TechtacularCategory category : chosen) {
Map<Integer, List<TechtacularQuestion>> byPoints = category.getQuestions().stream()
.collect(Collectors.groupingBy(TechtacularQuestion::getPoints));
List<TechtacularBoardView.Tile> tiles = new ArrayList<>();
for (int value : POINT_TIERS) {
List<TechtacularQuestion> pool = byPoints.get(value);
if (pool == null || pool.isEmpty()) {
continue;
}
// Bevorzugt Fragen, die nicht in der Vorrunde dran waren.
List<TechtacularQuestion> fresh = pool.stream()
.filter(q -> !excluded.contains(q.getId())).collect(Collectors.toList());
List<TechtacularQuestion> pick = fresh.isEmpty() ? pool : fresh;
TechtacularQuestion question = pick.get(random.nextInt(pick.size()));
List<TechtacularBoardView.Option> options = question.getAnswers().stream()
.map(a -> new TechtacularBoardView.Option(a.getId(), a.getText()))
.collect(Collectors.toList());
Collections.shuffle(options, random);
tiles.add(new TechtacularBoardView.Tile(question.getId(), value, question.getText(), options));
maxScore += value;
}
if (!tiles.isEmpty()) {
columns.add(new TechtacularBoardView.Category(category.getTitle(), tiles));
}
}
return new TechtacularBoardView(columns, maxScore);
}
/** Bewertet eine einzelne Antwort serverseitig (Frontend kennt die richtige Antwort vorher nicht). */
@Transactional(readOnly = true)
public AnswerResult checkAnswer(Long questionId, Long answerId) {
TechtacularQuestion question = questionRepository.findById(questionId).orElse(null);
if (question == null) {
return new AnswerResult(false, null, "", 0);
}
TechtacularAnswer correct = question.correctAnswer();
Long correctId = correct != null ? correct.getId() : null;
boolean isCorrect = correctId != null && correctId.equals(answerId);
return new AnswerResult(isCorrect, correctId, question.getExplanation(), isCorrect ? question.getPoints() : 0);
}
/** Schließt eine Runde ab: Score wird aus den tatsächlichen Antworten recomputed und gespeichert. */
@Transactional
public TechtacularResult finish(String username, FinishRequest request) {
int score = 0;
int maxScore = 0;
int correctCount = 0;
int total = 0;
if (request.getAnswers() != null) {
for (AnswerRequest answer : request.getAnswers()) {
if (answer.getQuestionId() == null) {
continue;
}
TechtacularQuestion question = questionRepository.findById(answer.getQuestionId()).orElse(null);
if (question == null) {
continue;
}
total++;
maxScore += question.getPoints();
TechtacularAnswer correct = question.correctAnswer();
if (correct != null && correct.getId().equals(answer.getAnswerId())) {
score += question.getPoints();
correctCount++;
}
}
}
int seconds = Math.max(request.getDurationSeconds(), 0);
ScoreResult saved = gameScoreService.recordScore(username, GAME, null, score, correctCount, seconds);
return new TechtacularResult(score, maxScore, correctCount, total,
saved.getHighscore(), saved.isNewHighscore(), saved.getPlays());
}
// ---------- Admin ----------
/** Leichte Übersicht: Kategorien mit Fragenanzahl (lädt nicht alle Fragen). */
@Transactional(readOnly = true)
public List<AdminCategoryRow> categoryRows() {
return categoryRepository.findAllByOrderBySortOrderAscIdAsc().stream()
.map(c -> new AdminCategoryRow(c.getId(), c.getSlug(), c.getTitle(), c.isActive(),
questionRepository.countByCategoryId(c.getId())))
.toList();
}
/** Eine Kategorie inkl. Fragen und Antworten (für die Detailseite). */
@Transactional(readOnly = true)
public TechtacularCategory categoryWithQuestions(Long id) {
TechtacularCategory category = categoryRepository.findById(id).orElse(null);
if (category != null) {
category.getQuestions().forEach(q -> q.getAnswers().size()); // lazy init
}
return category;
}
@Transactional
public void createCategory(String title) {
if (title == null || title.isBlank()) {
return;
}
String clean = title.trim();
int order = (int) categoryRepository.count() + 1;
categoryRepository.save(new TechtacularCategory(uniqueSlug(clean), clean, order, true));
}
@Transactional
public void addQuestion(Long categoryId, String text, String explanation, int points,
List<String> answers, int correctIndex) {
if (text == null || text.isBlank() || answers == null) {
return;
}
categoryRepository.findById(categoryId).ifPresent(category -> {
TechtacularQuestion question = new TechtacularQuestion(
text.trim(),
(explanation == null || explanation.isBlank()) ? null : explanation.trim(),
normalizePoints(points));
int sort = 0;
boolean hasCorrect = false;
for (int i = 0; i < answers.size(); i++) {
String answerText = answers.get(i);
if (answerText == null || answerText.isBlank()) {
continue;
}
boolean isCorrect = (i == correctIndex);
hasCorrect = hasCorrect || isCorrect;
question.addAnswer(new TechtacularAnswer(answerText.trim(), isCorrect, sort++));
}
// Nur sinnvolle Fragen speichern: mind. 2 Antworten und genau die markierte ist korrekt.
if (question.getAnswers().size() >= 2 && hasCorrect) {
category.addQuestion(question);
categoryRepository.save(category);
}
});
}
@Transactional
public void deleteQuestion(Long questionId) {
questionRepository.deleteById(questionId);
}
@Transactional
public void deleteCategory(Long categoryId) {
categoryRepository.deleteById(categoryId);
}
@Transactional
public void toggleCategory(Long categoryId) {
categoryRepository.findById(categoryId).ifPresent(c -> c.setActive(!c.isActive()));
}
private int normalizePoints(int points) {
int rounded = Math.round(points / 100f) * 100;
return Math.max(100, Math.min(500, rounded));
}
private String uniqueSlug(String title) {
String base = title.toLowerCase()
.replace("ä", "ae").replace("ö", "oe").replace("ü", "ue").replace("ß", "ss")
.replaceAll("[^a-z0-9]+", "-")
.replaceAll("(^-|-$)", "");
if (base.isBlank()) {
base = "kategorie";
}
String slug = base;
int counter = 2;
while (categoryRepository.existsBySlug(slug)) {
slug = base + "-" + counter++;
}
return slug;
}
}
@@ -0,0 +1,9 @@
package com.example.mindflux.service;
import com.example.mindflux.model.User;
public interface UserService {
User findByUsername(String username);
void save(User user);
void deleteByUsername(String username); // <-- Nur die Methodensignatur, ohne {}
}
@@ -0,0 +1,28 @@
package com.example.mindflux.service;
import com.example.mindflux.model.User;
import com.example.mindflux.repository.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@Service
public class UserServiceImpl implements UserService {
@Autowired
private UserRepository userRepository;
@Override
public User findByUsername(String username) {
return userRepository.findByUsername(username).orElse(null); // <-- Optional aufgelöst
}
@Override
public void save(User user) {
userRepository.save(user);
}
@Override
public void deleteByUsername(String username) {
userRepository.deleteByUsername(username);
}
}
@@ -1,19 +0,0 @@
package com.mindflux;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.Map;
@RestController
public class HelloController {
@GetMapping("/")
public Map<String, String> hello() {
return Map.of(
"app", "mindflux",
"status", "running",
"message", "Hello from Spring Boot 🚀, automatic deploy is working. :-)"
);
}
}
+40 -5
View File
@@ -1,8 +1,43 @@
server.port=8080
# =======================
# Datenbankverbindung (PostgreSQL)
# =======================
spring.datasource.url=jdbc:postgresql://postgres:5432/mindfluxdb
spring.datasource.username=mindflux
spring.datasource.password=mindflux_pass
spring.config.import=optional:file:.env[.properties]
spring.datasource.url=${MINDFLUX_DB_URL:jdbc:postgresql://localhost:5433/mindflux_db}
spring.datasource.username=${MINDFLUX_DB_USER:mindflux_user}
spring.datasource.password=${MINDFLUX_DB_PASSWORD}
spring.datasource.driver-class-name=org.postgresql.Driver
# =======================
# Hibernate / JPA
# =======================
spring.jpa.hibernate.ddl-auto=validate
spring.jpa.show-sql=true
spring.jpa.show-sql=false
spring.jpa.open-in-view=false
# =======================
# Datenbank-Migrationen
# =======================
spring.flyway.enabled=true
# =======================
# SQL-Initialisierung
# =======================
spring.sql.init.mode=never
# =======================
# Server
# =======================
server.port=8282
server.forward-headers-strategy=framework
server.servlet.session.cookie.secure=${MINDFLUX_COOKIE_SECURE:false}
server.servlet.session.cookie.http-only=true
server.servlet.session.cookie.same-site=lax
spring.output.ansi.enabled=ALWAYS
# Öffentliche Basis-URL, z. B. für künftig erzeugte absolute Links.
mindflux.public-url=${MINDFLUX_PUBLIC_URL:http://localhost:8282}
@@ -16,5 +16,4 @@ CREATE TABLE achievements (
date_achieved TIMESTAMP
);
CREATE INDEX idx_achievements_username
ON achievements (username);
CREATE INDEX idx_achievements_username ON achievements (username);
@@ -0,0 +1,14 @@
-- Generische Spiel-Ergebnistabelle für alle Mindflux-Spiele
-- (MindMatch ist das erste Spiel, das hier schreibt – die übrigen docken später an).
CREATE TABLE game_scores (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
username VARCHAR(100) NOT NULL,
game VARCHAR(50) NOT NULL,
deck VARCHAR(100),
score INT NOT NULL,
moves INT,
duration_seconds INT,
played_at TIMESTAMP NOT NULL
);
CREATE INDEX idx_game_scores_user_game ON game_scores (username, game);
@@ -0,0 +1,68 @@
-- MindMatch-Inhalte in die DB verlagern, damit Admins Decks (Kategorien) und
-- Paare jederzeit zur Laufzeit erweitern können (vorher statische JSON-Dateien).
CREATE TABLE mindmatch_decks (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
slug VARCHAR(100) NOT NULL UNIQUE,
title VARCHAR(150) NOT NULL,
sort_order INT NOT NULL DEFAULT 0,
active BOOLEAN NOT NULL DEFAULT TRUE
);
CREATE TABLE mindmatch_pairs (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
deck_id BIGINT NOT NULL REFERENCES mindmatch_decks (id) ON DELETE CASCADE,
term VARCHAR(255) NOT NULL,
match_text VARCHAR(255) NOT NULL
);
CREATE INDEX idx_mindmatch_pairs_deck ON mindmatch_pairs (deck_id);
-- Seed: die bisherigen 3 Decks plus das neue SQL-Befehle-Deck.
INSERT INTO mindmatch_decks (slug, title, sort_order, active) VALUES
('netzwerk', 'Netzwerk-Grundlagen', 1, TRUE),
('hardware', 'Hardware & Komponenten', 2, TRUE),
('it-sicherheit', 'IT-Sicherheit', 3, TRUE),
('sql-befehle', 'SQL-Befehle', 4, TRUE);
INSERT INTO mindmatch_pairs (deck_id, term, match_text)
SELECT d.id, v.term, v.match_text
FROM mindmatch_decks d
JOIN (
VALUES
('netzwerk', 'DNS', 'Löst Namen in IP-Adressen auf'),
('netzwerk', 'DHCP', 'Vergibt IP-Adressen automatisch'),
('netzwerk', 'Router', 'Verbindet verschiedene Netze'),
('netzwerk', 'Switch', 'Verbindet Geräte im LAN'),
('netzwerk', 'Gateway', 'Übergang in ein anderes Netz'),
('netzwerk', 'Firewall', 'Filtert den Netzwerkverkehr'),
('netzwerk', 'MAC-Adresse', 'Physische Hardware-Adresse'),
('netzwerk', 'Subnetzmaske', 'Trennt Netz- und Hostanteil'),
('hardware', 'CPU', 'Zentrale Recheneinheit'),
('hardware', 'RAM', 'Flüchtiger Arbeitsspeicher'),
('hardware', 'SSD', 'Schneller Flash-Speicher'),
('hardware', 'GPU', 'Grafikprozessor'),
('hardware', 'Mainboard', 'Hauptplatine des Rechners'),
('hardware', 'BIOS', 'Startet die Hardware'),
('hardware', 'Netzteil', 'Wandelt die Netzspannung um'),
('hardware', 'Cache', 'Schneller Zwischenspeicher der CPU'),
('it-sicherheit', 'Phishing', 'Täuschung zum Datenklau'),
('it-sicherheit', 'Verschlüsselung', 'Macht Daten unlesbar'),
('it-sicherheit', 'Backup', 'Sicherungskopie von Daten'),
('it-sicherheit', 'VPN', 'Verschlüsselter Tunnel'),
('it-sicherheit', '2FA', 'Zwei-Faktor-Anmeldung'),
('it-sicherheit', 'Malware', 'Schädliche Software'),
('it-sicherheit', 'Patch', 'Schließt Sicherheitslücken'),
('it-sicherheit', 'Brute Force', 'Systematisches Passwortraten'),
('sql-befehle', 'SELECT', 'Daten abfragen'),
('sql-befehle', 'INSERT', 'Datensatz einfügen'),
('sql-befehle', 'UPDATE', 'Datensatz ändern'),
('sql-befehle', 'DELETE', 'Datensatz löschen'),
('sql-befehle', 'WHERE', 'Zeilen filtern'),
('sql-befehle', 'JOIN', 'Tabellen verknüpfen'),
('sql-befehle', 'GROUP BY', 'Zeilen gruppieren'),
('sql-befehle', 'ORDER BY', 'Ergebnis sortieren')
) AS v(slug, term, match_text) ON v.slug = d.slug;
@@ -0,0 +1,152 @@
-- Weitere MindMatch-Decks aus dem Dokument "Memory-Kategorien – Fachinformatiker".
-- 5 Themen-Decks + die Oberkategorie "Abkürzungen" als 6 eigene Decks (Deck-Modell ist flach).
INSERT INTO mindmatch_decks (slug, title, sort_order, active) VALUES
('betriebssysteme', 'Betriebssysteme', 5, TRUE),
('programmierung', 'Programmierung', 6, TRUE),
('webentwicklung', 'Webentwicklung', 7, TRUE),
('softwareentwicklung', 'Softwareentwicklung', 8, TRUE),
('cloud-devops', 'Cloud & DevOps', 9, TRUE),
('abk-netzwerk', 'Abkürzungen: Netzwerk', 10, TRUE),
('abk-hardware', 'Abkürzungen: Hardware', 11, TRUE),
('abk-programmierung-datenformate','Abkürzungen: Programmierung & Datenformate', 12, TRUE),
('abk-web', 'Abkürzungen: Web', 13, TRUE),
('abk-it-sicherheit', 'Abkürzungen: IT-Sicherheit', 14, TRUE),
('abk-betriebssysteme-devops', 'Abkürzungen: Betriebssysteme & DevOps', 15, TRUE);
INSERT INTO mindmatch_pairs (deck_id, term, match_text)
SELECT d.id, v.term, v.match_text
FROM mindmatch_decks d
JOIN (
VALUES
-- Betriebssysteme
('betriebssysteme', 'Windows', 'Microsoft'),
('betriebssysteme', 'Linux', 'Open Source'),
('betriebssysteme', 'Kernel', 'Betriebssystemkern'),
('betriebssysteme', 'Prozess', 'Laufendes Programm'),
('betriebssysteme', 'Thread', 'Ausführungsstrang'),
('betriebssysteme', 'Dateisystem', 'Datenorganisation'),
('betriebssysteme', 'NTFS', 'Windows-Dateisystem'),
('betriebssysteme', 'ext4', 'Linux-Dateisystem'),
('betriebssysteme', 'Shell', 'Kommandozeile'),
('betriebssysteme', 'Terminal', 'Konsolenzugriff'),
('betriebssysteme', 'Dienst', 'Hintergrundprozess'),
('betriebssysteme', 'Rechte', 'Zugriffskontrolle'),
-- Programmierung
('programmierung', 'Variable', 'Speicherplatz'),
('programmierung', 'Schleife', 'Wiederholung'),
('programmierung', 'Array', 'Feld'),
('programmierung', 'Objekt', 'Instanz'),
('programmierung', 'Klasse', 'Bauplan'),
('programmierung', 'Methode', 'Funktion'),
('programmierung', 'Interface', 'Vertrag'),
('programmierung', 'Vererbung', 'OOP-Konzept'),
('programmierung', 'Exception', 'Fehlerbehandlung'),
('programmierung', 'Compiler', 'Übersetzer'),
('programmierung', 'Debugger', 'Fehlersuche'),
('programmierung', 'Git', 'Versionsverwaltung'),
-- Webentwicklung
('webentwicklung', 'HTML', 'Struktur'),
('webentwicklung', 'CSS', 'Gestaltung'),
('webentwicklung', 'JavaScript', 'Interaktivität'),
('webentwicklung', 'DOM', 'Dokumentenmodell'),
('webentwicklung', 'API', 'Programmierschnittstelle'),
('webentwicklung', 'JSON', 'Datenaustausch'),
('webentwicklung', 'REST', 'Architekturstil'),
('webentwicklung', 'HTTP', 'Übertragungsprotokoll'),
('webentwicklung', 'Cookie', 'Browserdaten'),
('webentwicklung', 'Session', 'Benutzersitzung'),
('webentwicklung', 'Backend', 'Serverlogik'),
('webentwicklung', 'Frontend', 'Benutzeroberfläche'),
-- Softwareentwicklung
('softwareentwicklung', 'Scrum', 'Agiles Vorgehen'),
('softwareentwicklung', 'Sprint', 'Entwicklungszyklus'),
('softwareentwicklung', 'Product Owner', 'Produktverantwortung'),
('softwareentwicklung', 'Kanban', 'Aufgabenfluss'),
('softwareentwicklung', 'UML', 'Modellierung'),
('softwareentwicklung', 'Use Case', 'Anwendungsfall'),
('softwareentwicklung', 'ER-Modell', 'Datenmodell'),
('softwareentwicklung', 'Testfall', 'Prüfung'),
('softwareentwicklung', 'CI/CD', 'Automatisierte Auslieferung'),
('softwareentwicklung', 'Refactoring', 'Codeverbesserung'),
('softwareentwicklung', 'Repository', 'Quellcodeablage'),
('softwareentwicklung', 'Merge', 'Zusammenführen'),
-- Cloud & DevOps
('cloud-devops', 'Docker', 'Container'),
('cloud-devops', 'Kubernetes', 'Container-Orchestrierung'),
('cloud-devops', 'VM', 'Virtuelle Maschine'),
('cloud-devops', 'Cloud', 'Ressourcen aus dem Internet'),
('cloud-devops', 'Azure', 'Microsoft Cloud'),
('cloud-devops', 'AWS', 'Amazon Web Services'),
('cloud-devops', 'GitHub', 'Codehosting'),
('cloud-devops', 'Jenkins', 'CI-Server'),
('cloud-devops', 'Pipeline', 'Automatisierung'),
('cloud-devops', 'YAML', 'Konfigurationsdatei'),
('cloud-devops', 'Deployment', 'Bereitstellung'),
('cloud-devops', 'Monitoring', 'Überwachung'),
-- Abkürzungen: Netzwerk
('abk-netzwerk', 'DNS', 'Domain Name System'),
('abk-netzwerk', 'DHCP', 'Dynamic Host Configuration Protocol'),
('abk-netzwerk', 'IP', 'Internet Protocol'),
('abk-netzwerk', 'TCP', 'Transmission Control Protocol'),
('abk-netzwerk', 'UDP', 'User Datagram Protocol'),
('abk-netzwerk', 'FTP', 'File Transfer Protocol'),
('abk-netzwerk', 'SSH', 'Secure Shell'),
('abk-netzwerk', 'VPN', 'Virtual Private Network'),
-- Abkürzungen: Hardware
('abk-hardware', 'CPU', 'Central Processing Unit'),
('abk-hardware', 'GPU', 'Graphics Processing Unit'),
('abk-hardware', 'RAM', 'Random Access Memory'),
('abk-hardware', 'ROM', 'Read Only Memory'),
('abk-hardware', 'SSD', 'Solid State Drive'),
('abk-hardware', 'HDD', 'Hard Disk Drive'),
('abk-hardware', 'PSU', 'Power Supply Unit'),
('abk-hardware', 'BIOS', 'Basic Input/Output System'),
('abk-hardware', 'UEFI', 'Unified Extensible Firmware Interface'),
('abk-hardware', 'PCIe', 'Peripheral Component Interconnect Express'),
-- Abkürzungen: Programmierung & Datenformate
('abk-programmierung-datenformate', 'SQL', 'Structured Query Language'),
('abk-programmierung-datenformate', 'IDE', 'Integrated Development Environment'),
('abk-programmierung-datenformate', 'SDK', 'Software Development Kit'),
('abk-programmierung-datenformate', 'OOP', 'Object Oriented Programming'),
('abk-programmierung-datenformate', 'CRUD', 'Create Read Update Delete'),
('abk-programmierung-datenformate', 'MVC', 'Model View Controller'),
('abk-programmierung-datenformate', 'ORM', 'Object Relational Mapping'),
('abk-programmierung-datenformate', 'XML', 'Extensible Markup Language'),
-- Abkürzungen: Web
('abk-web', 'URL', 'Uniform Resource Locator'),
('abk-web', 'URI', 'Uniform Resource Identifier'),
('abk-web', 'CDN', 'Content Delivery Network'),
('abk-web', 'SOAP', 'Simple Object Access Protocol'),
('abk-web', 'JWT', 'JSON Web Token'),
('abk-web', 'CORS', 'Cross Origin Resource Sharing'),
-- Abkürzungen: IT-Sicherheit
('abk-it-sicherheit', 'MFA', 'Multi Factor Authentication'),
('abk-it-sicherheit', '2FA', 'Two Factor Authentication'),
('abk-it-sicherheit', 'TLS', 'Transport Layer Security'),
('abk-it-sicherheit', 'AES', 'Advanced Encryption Standard'),
('abk-it-sicherheit', 'RSA', 'Rivest Shamir Adleman'),
('abk-it-sicherheit', 'PKI', 'Public Key Infrastructure'),
('abk-it-sicherheit', 'IDS', 'Intrusion Detection System'),
('abk-it-sicherheit', 'IPS', 'Intrusion Prevention System'),
('abk-it-sicherheit', 'SIEM', 'Security Information and Event Management'),
('abk-it-sicherheit', 'CVE', 'Common Vulnerabilities and Exposures'),
-- Abkürzungen: Betriebssysteme & DevOps
('abk-betriebssysteme-devops', 'CLI', 'Command Line Interface'),
('abk-betriebssysteme-devops', 'GUI', 'Graphical User Interface'),
('abk-betriebssysteme-devops', 'VM', 'Virtual Machine'),
('abk-betriebssysteme-devops', 'CI', 'Continuous Integration'),
('abk-betriebssysteme-devops', 'CD', 'Continuous Delivery'),
('abk-betriebssysteme-devops', 'LTS', 'Long Term Support'),
('abk-betriebssysteme-devops', 'FQDN', 'Fully Qualified Domain Name')
) AS v(slug, term, match_text) ON v.slug = d.slug;
@@ -0,0 +1,30 @@
-- TechTacular: IT-Quizduell im Jeopardy-Stil. Inhalte DB-basiert und Admin-pflegbar.
-- Kategorie -> Fragen -> Antworten (genau eine korrekt). Gefüllt wird per Seeder
-- aus den vorhandenen FinalFlux-Fragenkatalogen (siehe TechtacularSeeder).
CREATE TABLE techtacular_categories (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
slug VARCHAR(150) NOT NULL UNIQUE,
title VARCHAR(200) NOT NULL,
sort_order INT NOT NULL DEFAULT 0,
active BOOLEAN NOT NULL DEFAULT TRUE
);
CREATE TABLE techtacular_questions (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
category_id BIGINT NOT NULL REFERENCES techtacular_categories (id) ON DELETE CASCADE,
question_text VARCHAR(1000) NOT NULL,
explanation VARCHAR(1000),
points INT NOT NULL DEFAULT 100
);
CREATE TABLE techtacular_answers (
id BIGINT GENERATED BY DEFAULT AS IDENTITY PRIMARY KEY,
question_id BIGINT NOT NULL REFERENCES techtacular_questions (id) ON DELETE CASCADE,
answer_text VARCHAR(500) NOT NULL,
correct BOOLEAN NOT NULL DEFAULT FALSE,
sort_order INT NOT NULL DEFAULT 0
);
CREATE INDEX idx_techtacular_questions_cat ON techtacular_questions (category_id);
CREATE INDEX idx_techtacular_answers_q ON techtacular_answers (question_id);
@@ -0,0 +1,4 @@
-- Umstellung auf das echte Jeopardy-Format (umgekehrt) mit kuratierten Inhalten.
-- Der bisherige (templatehafte) FinalFlux-Import wird geleert; der TechtacularSeeder
-- befüllt anschließend neu aus techtacular/content.json.
TRUNCATE TABLE techtacular_categories RESTART IDENTITY CASCADE;
@@ -0,0 +1,165 @@
body {
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
background: linear-gradient(145deg, #1f1f2e, #2c2c3d);
color: #ffffff;
margin: 0;
padding: 0;
}
.achievements-container {
max-width: 1400px;
margin: 2rem auto;
padding: 2rem;
display: flex;
flex-direction: column;
gap: 2rem;
animation: fadeInUp 0.8s ease-out;
}
h1, h2 {
color: #00e5ff;
text-shadow: 0 0 5px rgba(0, 229, 255, 0.2);
text-align: center;
}
.slogan {
text-align: center;
color: #ccc;
margin-bottom: 2rem;
font-style: italic;
}
/* === Zurück-Button === */
.back-button {
position: absolute;
top: 20px;
left: 20px;
background-color: #00d9ff;
color: #0d1117;
padding: 10px 18px;
border-radius: 10px;
font-weight: bold;
text-decoration: none;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
transition: background-color 0.3s ease, transform 0.3s ease;
font-size: 1rem;
z-index: 1000;
}
.back-button:hover {
background-color: #00aacc;
transform: scale(1.05);
}
/* Responsives Verhalten */
@media (max-width: 768px) {
.back-button {
top: 10px;
left: 10px;
padding: 8px 14px;
font-size: 0.9rem;
}
}
.achievements-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
gap: 2rem;
}
.achievement-card {
background-color: rgba(10, 15, 25, 0.95);
padding: 2rem;
border-radius: 20px;
text-align: center;
box-shadow:
0 0 15px rgba(0, 229, 255, 0.07),
0 4px 10px rgba(0, 0, 0, 0.3);
backdrop-filter: blur(4px);
transition: transform 0.3s ease, box-shadow 0.3s ease;
}
.achievement-card:hover {
transform: scale(1.02);
box-shadow: 0 0 20px rgba(0, 229, 255, 0.2);
}
.trophy-icon {
font-size: 3rem;
margin-bottom: 1rem;
}
.achievement-card h2 {
margin-bottom: 0.5rem;
}
.achievement-card p {
margin: 0.5rem 0;
}
.status {
margin-top: 1rem;
font-weight: bold;
color: #00e5ff;
}
.locked {
opacity: 0.6;
filter: grayscale(70%);
}
/* === Unlock-Effekt für freigeschaltete Achievements === */
.achievement-card.unlocked {
animation: unlock-glow 1s ease-out;
}
/* Animation für Unlock-Glow */
@keyframes unlock-glow {
0% {
box-shadow: 0 0 0 rgba(0, 229, 255, 0);
transform: scale(1);
}
50% {
box-shadow: 0 0 20px rgba(0, 229, 255, 0.7);
transform: scale(1.05);
}
100% {
box-shadow: 0 0 10px rgba(0, 229, 255, 0.2);
transform: scale(1);
}
}
/* Sanftes Pulsieren beim Hover über freigeschaltete Achievements */
.achievement-card.unlocked:hover {
animation: pulse 1.5s infinite;
}
@keyframes pulse {
0% {
box-shadow: 0 0 10px rgba(0, 229, 255, 0.2);
}
50% {
box-shadow: 0 0 20px rgba(0, 229, 255, 0.5);
}
100% {
box-shadow: 0 0 10px rgba(0, 229, 255, 0.2);
}
}
/* === Footer === */
footer {
background-color: #111122;
padding: 1rem;
text-align: center;
font-size: 0.9rem;
color: #aaa;
}
footer a {
color: #66d9ef;
text-decoration: none;
margin: 0 0.5rem;
}
footer a:hover {
text-decoration: underline;
+273
View File
@@ -0,0 +1,273 @@
body.finalflux-shell,
body.finalflux-page {
background: var(--bg-glow), var(--bg);
color: var(--text);
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
}
.finalflux-shell {
min-height: 100vh;
display: grid;
grid-template-columns: 320px minmax(0, 1fr);
}
.finalflux-sidebar {
background: var(--surface);
border-right: 1px solid var(--border-accent);
padding: 1.5rem;
overflow-y: auto;
}
.finalflux-sidebar h1,
.finalflux-main h2,
.finalflux-main h3,
.finalflux-page h1,
.finalflux-page h2,
.finalflux-page h3 {
color: var(--accent);
}
.finalflux-sidebar p,
.finalflux-main p,
.finalflux-page p,
.finalflux-page li {
line-height: 1.65;
}
.finalflux-back,
.finalflux-page .back-link {
display: inline-block;
margin-bottom: 1rem;
padding: 0.65rem 1rem;
background: var(--accent);
color: var(--accent-ink);
border-radius: 8px;
font-weight: 700;
text-decoration: none;
}
.finalflux-nav section {
margin-top: 1.5rem;
}
.finalflux-nav h2 {
color: var(--accent-2);
font-size: 1rem;
margin-bottom: 0.7rem;
}
.finalflux-nav a {
display: block;
color: var(--muted);
text-decoration: none;
padding: 0.42rem 0.6rem;
border-radius: 6px;
}
.finalflux-nav a:hover {
background: var(--surface-2);
color: var(--accent);
}
.finalflux-main {
padding: 2rem;
max-width: 1100px;
}
.finalflux-hero,
.finalflux-panel,
.finalflux-page section {
background: var(--surface);
border-left: 4px solid var(--accent);
border-radius: 8px;
padding: 1.25rem;
margin-bottom: 1.5rem;
}
.finalflux-hero h2 {
font-size: 2rem;
margin: 0.4rem 0 1rem;
}
.eyebrow {
color: var(--accent-2);
font-weight: 700;
text-transform: uppercase;
letter-spacing: 0.08em;
}
.finalflux-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
gap: 1rem;
margin-bottom: 1.5rem;
}
.finalflux-grid article,
.fluxcheck {
background: var(--surface);
border: 1px solid var(--border-accent);
border-radius: 8px;
padding: 1rem;
}
.finalflux-actions {
display: flex;
flex-wrap: wrap;
gap: 0.75rem;
margin-top: 1rem;
}
.finalflux-actions a,
.fluxcheck button {
background: var(--accent);
color: var(--accent-ink);
border: 0;
border-radius: 8px;
cursor: pointer;
font-weight: 700;
padding: 0.65rem 1rem;
text-decoration: none;
}
.finalflux-page {
padding: 2rem;
}
.finalflux-page main {
display: block;
max-width: 980px;
margin: 0 auto;
padding: 0;
}
.finalflux-page code {
background: var(--surface-2);
border-radius: 4px;
color: var(--accent-2);
padding: 0.15rem 0.35rem;
}
.key-list {
padding-left: 1.2rem;
}
.fluxcheck label {
display: block;
margin: 0.5rem 0;
}
.fluxcheck-result {
font-weight: 700;
margin-top: 0.8rem;
}
.fluxcheck-result.correct {
color: #00ff88;
}
.fluxcheck-result.wrong {
color: #ff6b6b;
}
.finalflux-test {
background: var(--surface);
border-left: 4px solid var(--accent);
border-radius: 8px;
padding: 1.25rem;
margin-bottom: 1.5rem;
}
.test-meta {
display: flex;
flex-wrap: wrap;
gap: 0.75rem;
justify-content: space-between;
color: var(--accent-2);
font-weight: 700;
margin-bottom: 1rem;
}
.category-block {
background: var(--surface-2);
border: 1px solid var(--border-accent);
border-radius: 8px;
padding: 1rem;
margin-bottom: 1rem;
}
.category-block h2 {
margin: 0.2rem 0 0.5rem;
}
.question-card {
background: var(--bg);
border-radius: 8px;
padding: 1rem;
}
.answer-options {
display: grid;
gap: 0.65rem;
margin: 1rem 0;
}
.answer-options label {
align-items: flex-start;
background: var(--surface);
border: 1px solid var(--border-accent);
border-radius: 8px;
cursor: pointer;
display: flex;
gap: 0.65rem;
padding: 0.75rem;
}
.answer-options label:hover {
border-color: var(--accent);
}
.test-actions {
display: flex;
flex-wrap: wrap;
gap: 0.75rem;
margin-top: 1rem;
}
.test-actions button,
[data-restart-test] {
background: var(--accent);
border: 0;
border-radius: 8px;
color: var(--accent-ink);
cursor: pointer;
font-weight: 700;
padding: 0.65rem 1rem;
}
.test-actions button.secondary {
background: var(--surface-2);
border: 1px solid var(--border-accent);
color: var(--text);
}
.test-actions button:disabled {
cursor: not-allowed;
opacity: 0.45;
}
@media (max-width: 820px) {
.finalflux-shell {
grid-template-columns: 1fr;
}
.finalflux-sidebar {
border-right: 0;
border-bottom: 1px solid var(--border-accent);
}
.finalflux-main,
.finalflux-page {
padding: 1rem;
}
}
+351
View File
@@ -0,0 +1,351 @@
/* === MindMatch === Farben über zentrale Theme-Tokens (theme.css):
Dark = Grün-Neon, Light = heller Grund + Magenta. Layout: feste Viewport-Höhe,
kein Scrollen – das Spielfeld füllt den verbleibenden Platz und skaliert die Karten. */
/* Overlay-Einblendung (kam früher aus style.css). */
@keyframes fadeInUp {
0% { opacity: 0; transform: translateY(20px); }
100% { opacity: 1; transform: translateY(0); }
}
/* body bekommt Layout (Shell füllt 100vh über flex:1). Farben/Hintergrund liefert theme.css. */
body.mm-body {
height: 100vh;
min-height: 100vh;
overflow: hidden; /* Seite scrollt nie */
display: flex;
flex-direction: column;
color: var(--text);
}
.mm-shell {
flex: 1; /* body ist flex-column -> Shell füllt 100vh */
min-height: 0;
display: flex;
flex-direction: column;
padding: 0.6rem 0.85rem;
gap: 0.55rem;
}
/* --- Kopfzeile (kompakt) --- */
.mm-header {
flex: 0 0 auto;
display: flex;
align-items: center;
justify-content: space-between;
padding: 0.5rem 1.1rem;
background-color: var(--surface);
border: 1px solid var(--border);
border-radius: 12px;
box-shadow: var(--g-soft), 0 0 8px var(--glow-w);
}
.mm-header-tools {
display: flex;
align-items: center;
gap: 0.7rem;
}
.mm-title {
font-size: 1.3rem;
color: var(--accent);
margin: 0;
text-shadow: 0 0 8px var(--glow-s);
}
.mm-back, .mm-logout { text-decoration: none; font-weight: bold; }
.mm-back { color: var(--accent); }
.mm-logout { color: var(--danger); }
/* --- Leiste: Steuerung + Werte --- */
.mm-bar {
flex: 0 0 auto;
display: flex;
align-items: center;
justify-content: space-between;
flex-wrap: wrap;
gap: 0.55rem 0.85rem;
}
.mm-bar-group {
display: flex;
align-items: center;
flex-wrap: wrap;
gap: 0.5rem;
}
.mm-field {
display: flex;
align-items: center;
gap: 0.45rem;
font-weight: 700;
color: var(--accent);
}
.mm-field select {
padding: 0.5rem 0.7rem;
border-radius: 8px;
border: 1px solid var(--border-accent);
background: var(--surface-2);
color: var(--text);
font-size: 0.95rem;
min-width: 200px;
}
.mm-btn {
padding: 0.5rem 1.1rem;
border: 0;
border-radius: 8px;
background: var(--accent);
color: var(--accent-ink);
font-weight: 700;
font-size: 0.95rem;
cursor: pointer;
text-decoration: none;
display: inline-block;
box-shadow: 0 0 14px var(--glow-w);
transition: filter 0.25s ease, transform 0.15s ease, background-color 0.25s ease;
}
.mm-btn:hover { filter: brightness(1.08); transform: translateY(-2px); }
.mm-btn-secondary {
background: var(--surface-2);
border: 1px solid var(--border-accent);
color: var(--text);
box-shadow: none;
}
/* Abbrechen-Button (rötlich, klar als Abbruch erkennbar) */
.mm-btn-cancel {
background: rgba(255, 107, 107, 0.14);
border: 1px solid rgba(255, 107, 107, 0.55);
color: var(--danger);
box-shadow: none;
}
.mm-btn-cancel:hover {
background: rgba(255, 107, 107, 0.28);
color: #ffffff;
}
/* Damit das hidden-Attribut den display:inline-block der .mm-btn überstimmt */
.mm-btn[hidden] { display: none; }
/* --- HUD als kompakte Chips --- */
.mm-hud { gap: 0.4rem; }
.mm-stat {
display: inline-flex;
align-items: baseline;
gap: 0.4rem;
padding: 0.35rem 0.7rem;
background: var(--surface-2);
border: 1px solid var(--border);
border-radius: 10px;
font-size: 0.72rem;
text-transform: uppercase;
letter-spacing: 0.05em;
color: var(--muted);
white-space: nowrap;
}
.mm-stat b { font-size: 1.05rem; color: var(--accent); }
/* --- Spielfeld: füllt den Rest, kein Scrollen --- */
.mm-stage {
flex: 1;
min-height: 0;
display: flex;
justify-content: center;
overflow: hidden;
}
.mm-board {
display: grid;
gap: clamp(0.3rem, 1.2vmin, 0.75rem);
width: 100%;
height: 100%;
min-height: 0;
margin: 0 auto;
/* grid-template-columns + max-width werden per JS gesetzt;
gleich hohe Reihen über grid-auto-rows, damit alles in die Höhe passt. */
grid-auto-rows: 1fr;
}
.mm-idle {
margin: auto;
color: var(--muted);
text-align: center;
padding: 2rem 1rem;
font-size: 1rem;
}
/* --- Karte (füllt ihre Zelle) --- */
.mm-card {
position: relative;
min-width: 0;
min-height: 0;
perspective: 900px;
cursor: pointer;
border: 0;
background: transparent;
padding: 0;
}
.mm-card-inner {
position: absolute;
inset: 0;
transform-style: preserve-3d;
transition: transform 0.45s ease;
}
.mm-card.flipped .mm-card-inner,
.mm-card.matched .mm-card-inner {
transform: rotateY(180deg);
}
.mm-card-face {
position: absolute;
inset: 0;
display: flex;
align-items: center;
justify-content: center;
text-align: center;
padding: 0.4rem;
border-radius: 10px;
overflow: hidden;
backface-visibility: hidden;
-webkit-backface-visibility: hidden;
}
/* Rückseite (verdeckt): leuchtendes Mindflux-Emblem statt ⚡ */
.mm-card-front {
background: linear-gradient(145deg, var(--surface), var(--surface-2));
border: 1px solid var(--border-accent);
box-shadow: inset 0 0 18px var(--glow-w);
font-size: 0; /* versteckt das alte ⚡-Zeichen */
}
.mm-card-front::after {
content: "";
display: block;
width: 56%;
height: 56%;
background: var(--accent);
-webkit-mask: url("/img/mindflux-emblem.png") center/contain no-repeat;
mask: url("/img/mindflux-emblem.png") center/contain no-repeat;
filter: drop-shadow(0 0 9px var(--glow-s));
}
/* Vorderseite (Inhalt) */
.mm-card-back {
background: var(--surface);
border: 1px solid var(--border-accent);
transform: rotateY(180deg);
flex-direction: column;
gap: 0.2rem;
color: var(--text);
font-weight: 600;
line-height: 1.2;
hyphens: auto;
}
.mm-card-back.mm-term {
color: var(--accent);
font-size: clamp(0.72rem, 1.7vw, 1.15rem);
font-weight: 800;
}
.mm-card-back.mm-def {
font-size: clamp(0.62rem, 1.25vw, 0.9rem);
}
.mm-kind {
font-size: clamp(0.5rem, 1vw, 0.65rem);
text-transform: uppercase;
letter-spacing: 0.08em;
color: var(--muted);
opacity: 0.9;
}
.mm-text {
overflow: hidden;
display: -webkit-box;
-webkit-line-clamp: 4;
-webkit-box-orient: vertical;
}
.mm-card:not(.matched):hover .mm-card-front {
border-color: var(--accent);
box-shadow: 0 0 14px var(--glow-s), inset 0 0 18px var(--glow-w);
}
.mm-card.matched { cursor: default; }
.mm-card.matched .mm-card-back {
border-color: #00ff88;
box-shadow: 0 0 14px rgba(0, 255, 136, 0.3);
animation: mm-pop 0.4s ease;
}
@keyframes mm-pop {
0% { transform: rotateY(180deg) scale(1); }
50% { transform: rotateY(180deg) scale(1.06); }
100% { transform: rotateY(180deg) scale(1); }
}
.mm-card.wrong .mm-card-back {
border-color: #ff6b6b;
box-shadow: 0 0 14px rgba(255, 107, 107, 0.3);
}
/* --- Ergebnis-Overlay --- */
.mm-result {
position: fixed;
inset: 0;
display: flex;
align-items: center;
justify-content: center;
background: var(--bg-glow), rgba(0, 0, 0, 0.55);
backdrop-filter: blur(4px);
z-index: 1000;
}
.mm-result[hidden] { display: none; }
.mm-result-card {
background: var(--surface);
border: 1px solid var(--border-accent);
border-radius: 18px;
padding: 2rem 2.5rem;
text-align: center;
max-width: 420px;
width: 90%;
box-shadow: 0 0 30px var(--glow-w);
animation: fadeInUp 0.5s ease-out;
}
.mm-result-card h2 { color: var(--accent); margin-bottom: 0.5rem; }
.mm-stars { font-size: 1.8rem; letter-spacing: 0.2rem; margin-bottom: 0.5rem; color: var(--accent); }
.mm-result-score { font-size: 1.3rem; margin-bottom: 0.3rem; color: var(--text); }
.mm-result-score strong { color: var(--accent); }
.mm-result-detail { color: var(--muted); font-size: 0.95rem; margin-bottom: 0.6rem; }
.mm-result-highscore { color: #00ff88; font-weight: 800; margin-bottom: 1rem; }
.mm-result-highscore[hidden] { display: none; }
.mm-result-actions {
display: flex;
flex-wrap: wrap;
gap: 0.75rem;
justify-content: center;
margin-top: 1rem;
}
/* --- Mobil --- */
@media (max-width: 600px) {
.mm-header { padding: 0.45rem 0.8rem; }
.mm-title { font-size: 1.15rem; }
.mm-field select { min-width: 150px; }
.mm-stat { font-size: 0.65rem; padding: 0.3rem 0.55rem; }
.mm-stat b { font-size: 0.95rem; }
}
+184
View File
@@ -0,0 +1,184 @@
/* === Zurück-Button === */
.back-button {
position: absolute;
top: 20px;
left: 20px;
background-color: #00d9ff;
color: #0d1117;
padding: 10px 18px;
border-radius: 10px;
font-weight: bold;
text-decoration: none;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
transition: background-color 0.3s ease, transform 0.3s ease;
font-size: 1rem;
z-index: 1000;
}
.back-button:hover {
background-color: #00aacc;
transform: scale(1.05);
}
/* Responsives Verhalten */
@media (max-width: 768px) {
.back-button {
top: 10px;
left: 10px;
padding: 8px 14px;
font-size: 0.9rem;
}
}
body {
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
background: linear-gradient(145deg, #1f1f2e, #2c2c3d);
color: #ffffff;
margin: 0;
padding: 0;
}
.progress-container {
max-width: 1400px;
margin: 2rem auto;
padding: 2rem;
display: flex;
flex-direction: column;
gap: 2rem;
animation: fadeInUp 0.8s ease-out;
}
h1, h2, h3 {
color: #00e5ff;
text-shadow: 0 0 5px rgba(0, 229, 255, 0.2);
}
/* === Gesamtfortschritt === */
.section-overall-progress {
display: flex;
justify-content: space-between;
align-items: stretch;
flex-wrap: wrap;
gap: 2rem;
}
.progress-summary {
display: flex;
flex: 1;
gap: 2rem;
background: rgba(0, 9, 22, 0.95);
padding: 2rem;
border-radius: 20px;
box-shadow:
0 0 15px rgba(0, 229, 255, 0.05),
0 4px 10px rgba(0, 0, 0, 0.3);
backdrop-filter: blur(4px);
}
.circular-progress {
position: relative;
width: 160px;
height: 160px;
}
.percentage-label {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
font-size: 1.6rem;
font-weight: bold;
}
/* XP-Leiste */
.xp-bar {
background-color: #1a1a2e;
border-radius: 10px;
overflow: hidden;
height: 20px;
margin: 0.5rem 0;
}
.xp-fill {
height: 100%;
background: linear-gradient(90deg, #00e5ff, #4cc3dd);
}
/* === Lernzeitbereich === */
.section-learn-time {
background: rgba(0, 9, 22, 0.9);
padding: 1.5rem;
border-radius: 20px;
box-shadow:
0 0 10px rgba(0, 229, 255, 0.05),
0 4px 10px rgba(0, 0, 0, 0.3);
max-width: 600px;
margin: 0 auto;
}
#learnTimeChart {
max-width: 100%;
height: 180px !important;
}
/* === Spielkarten === */
.section-game-progress {
display: flex;
flex-direction: column;
gap: 1rem;
}
.game-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
gap: 1.5rem;
}
.game-card {
background-color: rgba(10, 15, 25, 0.95);
padding: 1.5rem;
border-radius: 16px;
box-shadow:
0 0 15px rgba(0, 229, 255, 0.07),
0 4px 10px rgba(0, 0, 0, 0.3);
backdrop-filter: blur(4px);
transition: transform 0.2s ease;
}
.game-card:hover {
transform: scale(1.02);
}
.game-progress-bar {
background-color: #1a1a2e;
border-radius: 10px;
overflow: hidden;
height: 10px;
margin: 0.5rem 0;
}
.game-progress-bar .fill {
height: 100%;
background-color: #00e5ff;
}
/* === Footer === */
footer {
background-color: #111122;
padding: 1rem;
text-align: center;
font-size: 0.9rem;
color: #aaa;
}
footer a {
color: #66d9ef;
text-decoration: none;
margin: 0 0.5rem;
}
footer a:hover {
text-decoration: underline;
+207
View File
@@ -0,0 +1,207 @@
body {
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
background: linear-gradient(145deg, #1f1f2e, #2c2c3d);
color: #ffffff;
margin: 0;
padding: 0;
}
header {
position: relative; /* wichtig für .back-button */
text-align: center;
padding: 2rem 1rem 1rem;
margin-bottom: 1rem;
}
header h1 {
font-size: 2.5rem;
color: #00e5ff;
margin-bottom: 0.5rem;
}
header .slogan {
font-size: 1.2rem;
color: #ccc;
text-shadow: 0 0 5px rgba(0, 229, 255, 0.2);
}
/* === Zurück-Button === */
.back-button {
position: absolute;
top: 20px;
left: 20px;
background-color: #00d9ff;
color: #0d1117;
padding: 10px 18px;
border-radius: 10px;
font-weight: bold;
text-decoration: none;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
transition: background-color 0.3s ease, transform 0.3s ease;
font-size: 1rem;
z-index: 1000;
}
.back-button:hover {
background-color: #00aacc;
transform: scale(1.05);
}
/* Responsives Verhalten */
@media (max-width: 768px) {
.back-button {
top: 10px;
left: 10px;
padding: 8px 14px;
font-size: 0.9rem;
}
}
@media (max-width: 480px) {
.back-button {
top: 8px;
left: 8px;
padding: 6px 10px;
font-size: 0.8rem;
}
}
.settings-container {
max-width: 1000px;
margin: 2rem auto;
padding: 2rem;
background: rgba(0, 9, 22, 0.95);
border-radius: 20px;
box-shadow:
0 0 15px rgba(0, 229, 255, 0.05),
0 4px 10px rgba(0, 0, 0, 0.3);
backdrop-filter: blur(4px);
display: flex;
flex-direction: column;
gap: 2rem;
}
.section {
background-color: rgba(10, 15, 25, 0.95);
padding: 1.5rem;
border-radius: 16px;
box-shadow: 0 0 10px rgba(0, 229, 255, 0.1);
transition: transform 0.3s ease;
}
.section:hover {
transform: translateY(-5px);
box-shadow: 0 6px 20px rgba(0, 229, 255, 0.2);
}
.section h2 {
margin-bottom: 1rem;
color: #00e5ff;
}
.switch-row {
display: flex;
justify-content: space-between;
align-items: center;
margin: 1rem 0;
}
.switch {
position: relative;
display: inline-block;
width: 50px;
height: 26px;
}
.switch input {
opacity: 0;
width: 0;
height: 0;
}
.slider {
position: absolute;
cursor: pointer;
top: 0; left: 0; right: 0; bottom: 0;
background-color: #888;
transition: 0.4s;
border-radius: 34px;
}
.slider:before {
position: absolute;
content: "";
height: 18px;
width: 18px;
left: 4px;
bottom: 4px;
background-color: white;
transition: 0.4s;
border-radius: 50%;
}
input:checked + .slider {
background-color: #00e5ff;
}
input:checked + .slider:before {
transform: translateX(24px);
}
.settings-form {
display: flex;
flex-direction: column;
gap: 1rem;
}
.settings-form input {
padding: 0.8rem;
border-radius: 8px;
border: none;
background: #1a1a2e;
color: #fff;
}
.settings-form button {
padding: 0.8rem;
border: none;
border-radius: 8px;
background-color: #00e5ff;
color: #00172e;
font-weight: bold;
cursor: pointer;
transition: background-color 0.3s ease, transform 0.2s ease;
}
.settings-form button:hover {
background-color: #4cc3dd;
transform: scale(1.02);
}
.danger-zone button {
background-color: #ff4d4d;
color: #fff;
}
.danger-zone button:hover {
background-color: #cc0000;
}
/* === Footer === */
footer {
background-color: #111122;
padding: 1rem;
text-align: center;
font-size: 0.9rem;
color: #aaa;
}
footer a {
color: #66d9ef;
text-decoration: none;
margin: 0 0.5rem;
}
footer a:hover {
text-decoration: underline;
}
@@ -0,0 +1,78 @@
body {
background-color: #0d1117;
color: #00d9ff;
font-family: 'Poppins', sans-serif; /* oder deine Mindflux-Schrift */
display: flex;
justify-content: center;
align-items: center;
height: 100vh;
margin: 0;
text-align: center;
}
.container {
padding: 40px;
border: 1px solid #00d9ff; /* feiner als dashed */
border-radius: 20px;
background-color: #121826;
box-shadow: 0 0 15px rgba(0, 217, 255, 0.5);
}
h1 {
font-size: 2.2rem;
margin-bottom: 20px;
}
p {
font-size: 1.1rem;
}
.time-machine {
font-size: 2.5rem;
margin: 20px 0;
}
.small-hint {
font-size: 0.9rem;
margin-top: 20px;
color: #7f8c8d;
}
.back-button {
position: absolute;
top: 20px;
left: 20px;
background-color: #00d9ff;
color: #0d1117;
padding: 10px 18px;
border-radius: 10px;
font-weight: bold;
text-decoration: none;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
transition: background-color 0.3s ease, transform 0.3s ease;
font-size: 1rem;
z-index: 1000;
}
.back-button:hover {
background-color: #00aacc;
transform: scale(1.05); /* leichter "Hover-Zoom" */
}
/* Responsives Verhalten */
@media (max-width: 768px) {
.back-button {
top: 10px;
left: 10px;
padding: 8px 14px;
font-size: 0.9rem;
}
}
@media (max-width: 480px) {
.back-button {
top: 8px;
left: 8px;
padding: 6px 10px;
font-size: 0.8rem;
}
}
+551
View File
@@ -0,0 +1,551 @@
/* === Reset === */
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
/* === Animationen === */
@keyframes fadeInUp {
0% {
opacity: 0;
transform: translateY(20px);
}
100% {
opacity: 1;
transform: translateY(0);
}
}
/* Glanz-Effekt für Hover */
@keyframes shine {
0% {
background-position: -100%;
}
100% {
background-position: 200%;
}
}
/* Fade-In für Container beim Laden */
@keyframes fadeInUp {
0% {
opacity: 0;
transform: translateY(20px);
}
100% {
opacity: 1;
transform: translateY(0);
}
}
/* === Body Hintergrund === */
body {
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
background: linear-gradient(145deg, #1f1f2e, #2c2c3d);
color: #ffffff;
min-height: 100vh;
display: flex;
flex-direction: column;
}
/* === Header === */
header {
text-align: center;
padding: 2rem;
margin: 2rem auto 1rem;
width: 90%;
max-width: 1200px;
background-color: #000916;
border-radius: 20px;
box-shadow:
0 8px 20px rgba(0, 229, 255, 0.15),
0 4px 12px rgba(0, 0, 0, 0.4);
transition: all 0.3s ease-in-out;
animation: fadeInUp 0.8s ease-out;
}
header:hover {
box-shadow:
0 10px 30px rgba(0, 229, 255, 0.25),
0 6px 16px rgba(0, 0, 0, 0.5);
}
.logo {
max-height: 350px;
width: auto;
margin-bottom: 1rem;
}
header img {
max-height: 80px;
margin-bottom: 1rem;
}
header p.slogan {
font-style: italic;
color: #00e5ff;
font-size: 1.1rem;
letter-spacing: 0.5px;
text-shadow: 0 0 5px rgba(0, 229, 255, 0.2);
}
/* === Main Bereich === */
main {
display: flex;
justify-content: center;
flex-wrap: wrap;
gap: 2rem;
padding: 2rem;
flex: 1;
width: 90%;
max-width: 1200px;
margin: 0 auto;
animation: fadeInUp 0.8s ease-out;
}
/* === Info-Textfeld === */
.info-box {
flex: 1 1 400px;
max-width: 600px;
background: rgba(0, 9, 22, 0.9);
padding: 2rem;
border-radius: 16px;
box-shadow:
0 0 15px rgba(0, 229, 255, 0.05),
0 4px 10px rgba(0, 0, 0, 0.3);
backdrop-filter: blur(4px);
animation: fadeInUp 0.9s ease-out;
}
/* === Login/Register Box === */
.login-box {
flex: 1 1 300px;
max-width: 400px;
background: rgba(10, 15, 25, 0.95);
padding: 2rem;
border-radius: 16px;
box-shadow:
0 0 15px rgba(0, 229, 255, 0.07),
0 4px 10px rgba(0, 0, 0, 0.3);
backdrop-filter: blur(4px);
animation: fadeInUp 1s ease-out;
}
.login-box h2 {
margin-bottom: 1rem;
color: #66d9ef;
}
.login-box form {
display: flex;
flex-direction: column;
}
.login-box input,
.login-box button {
padding: 0.75rem;
margin-bottom: 1rem;
border: none;
border-radius: 6px;
font-size: 1rem;
}
/* === Input === */
.login-box input {
background-color: #ffffff;
color: #000;
}
/* === Button mit Glanz- und Licht-Effekt === */
.login-box button {
background-color: #00e5ff;
color: #000;
font-weight: bold;
cursor: pointer;
position: relative;
overflow: hidden;
transition: background-color 0.3s ease-in-out, transform 0.2s ease;
box-shadow: 0 0 10px rgba(0, 229, 255, 0.3);
}
.login-box button::before {
content: '';
position: absolute;
top: 0;
left: -75%;
width: 50%;
height: 100%;
background: linear-gradient(
120deg,
rgba(255, 255, 255, 0.2) 0%,
rgba(255, 255, 255, 0.5) 50%,
rgba(255, 255, 255, 0.2) 100%
);
transform: skewX(-20deg);
animation: shine 2s infinite;
}
.login-box button:hover {
background-color: #4cc3dd;
transform: scale(1.02);
box-shadow: 0 0 15px rgba(0, 229, 255, 0.4), 0 0 30px rgba(0, 229, 255, 0.1) inset;
}
/* === Footer === */
footer {
background-color: #111122;
padding: 1rem;
text-align: center;
font-size: 0.9rem;
color: #aaa;
}
footer a {
color: #66d9ef;
text-decoration: none;
margin: 0 0.5rem;
}
footer a:hover {
text-decoration: underline;
}
.theme-toggle {
position: absolute;
top: 16px;
right: 16px;
z-index: 10;
}
/* Kleinere Switch-Größe */
.switch {
position: relative;
display: inline-block;
width: 42px;
height: 22px;
}
.switch input {
opacity: 0;
width: 0;
height: 0;
}
.slider {
position: absolute;
cursor: pointer;
top: 0; left: 0; right: 0; bottom: 0;
background-color: #888;
transition: 0.4s;
border-radius: 30px;
box-shadow: 0 0 6px rgba(0, 229, 255, 0.3);
display: flex;
align-items: center;
justify-content: space-between;
padding: 0 6px;
font-size: 0.8rem;
color: silver;
}
.slider:before {
content: "";
position: absolute;
height: 16px;
width: 16px;
left: 3px;
bottom: 3px;
background-color: #fff;
transition: 0.4s;
border-radius: 50%;
}
/* Bei aktiviertem Switch */
input:checked + .slider {
background-color: #00e5ff;
color: #fff;
}
input:checked + .slider:before {
transform: translateX(20px);
}
.icon {
pointer-events: none;
user-select: none;
}
.dashboard-tile {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
background-color: rgba(0, 9, 22, 0.95);
border-radius: 20px;
padding: 2rem;
width: 100%;
height: 100%;
text-decoration: none;
color: #00e5ff;
font-weight: bold;
font-size: 1.2rem;
box-shadow:
0 0 10px rgba(0, 229, 255, 0.1),
0 4px 12px rgba(0, 0, 0, 0.3);
transition: all 0.3s ease-in-out;
}
.dashboard-tile:hover {
background-color: rgba(0, 229, 255, 0.1);
transform: translateY(-3px);
box-shadow:
0 6px 16px rgba(0, 229, 255, 0.2),
0 0 20px rgba(0, 229, 255, 0.1) inset;
}
.dashboard-tile span {
color: #00e5ff;
text-shadow: 0 0 5px rgba(0, 229, 255, 0.2);
}
/* === Profilbereich === */
.profile-container {
max-width: 800px;
margin: 2rem auto;
background: rgba(0, 9, 22, 0.95);
padding: 2rem;
border-radius: 20px;
box-shadow: 0 0 20px rgba(0, 229, 255, 0.1);
animation: fadeInUp 0.8s ease-out;
}
.profile-form {
display: flex;
flex-direction: column;
gap: 1rem;
margin-bottom: 2rem;
}
.profile-form label {
font-weight: bold;
color: #00e5ff;
}
.profile-form input {
padding: 0.75rem;
background-color: #1a1a2e;
color: #fff;
border: none;
border-radius: 8px;
font-size: 1rem;
}
.btn {
padding: 0.75rem 1.5rem;
border: none;
border-radius: 8px;
font-weight: bold;
cursor: pointer;
transition: 0.3s ease;
}
.btn.save {
background-color: #00e5ff;
color: #00172e;
}
.btn.save:hover {
background-color: #4cc3dd;
}
.btn.danger {
background-color: #ff4d4d;
color: white;
}
.btn.danger:hover {
background-color: #cc0000;
}
/* Profilbild */
.profile-picture img {
max-height: 150px;
border-radius: 12px;
margin-bottom: 1rem;
}
/* === Tab-Navigation oben === */
.tab-nav {
display: flex;
justify-content: center;
gap: 1rem;
margin: 1rem auto 2rem;
flex-wrap: wrap;
}
.tab-nav .tab {
padding: 0.6rem 1.2rem;
background-color: rgba(0, 229, 255, 0.1);
color: #00e5ff;
border-radius: 12px;
text-decoration: none;
font-weight: bold;
transition: all 0.3s ease-in-out;
box-shadow: 0 2px 6px rgba(0, 229, 255, 0.1);
}
.tab-nav .tab:hover {
background-color: rgba(0, 229, 255, 0.25);
transform: translateY(-2px);
box-shadow: 0 4px 10px rgba(0, 229, 255, 0.2);
}
.tab-nav .tab.active {
background-color: #00e5ff;
color: #000;
}
.success-message {
background-color: #00d9ff;
color: #0d1117;
padding: 1rem;
margin: 1rem auto;
max-width: 600px;
border-radius: 10px;
text-align: center;
font-weight: bold;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
}
.success-message {
background-color: #00d9ff;
color: #0d1117;
padding: 1rem;
margin: 1rem auto;
max-width: 600px;
border-radius: 10px;
text-align: center;
font-weight: bold;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
opacity: 1;
transition: opacity 1.5s ease-out;
}
.back-button {
position: absolute;
top: 20px;
left: 20px;
background-color: #00e5ff;
color: #0d1117;
padding: 10px 18px;
border-radius: 10px;
font-weight: bold;
text-decoration: none;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
transition: background-color 0.3s ease, transform 0.3s ease;
font-size: 1rem;
z-index: 1000;
}
.back-button {
position: absolute;
top: 20px;
left: 20px;
background-color: #00d9ff;
color: #0d1117;
padding: 10px 18px;
border-radius: 10px;
font-weight: bold;
text-decoration: none;
box-shadow: 0 0 10px rgba(0, 217, 255, 0.5);
transition: background-color 0.3s ease, transform 0.3s ease;
font-size: 1rem;
z-index: 1000;
}
.back-button:hover {
background-color: #00aacc;
transform: scale(1.05);
}
@media (max-width: 768px) {
.back-button {
top: 10px;
left: 10px;
padding: 8px 14px;
font-size: 0.9rem;
}
}
<style>
/* Admin-Button Stil */
.admin-btn {
background-color: #00e5ff;
color: #0d1117;
padding: 0.5rem 1rem;
border-radius: 8px;
text-decoration: none;
font-weight: bold;
transition: background-color 0.3s, box-shadow 0.3s, transform 0.3s;
box-shadow: 0 0 10px rgba(0, 229, 255, 0.3);
}
.admin-btn:hover {
background-color: #4cc3dd;
box-shadow: 0 0 15px rgba(0, 229, 255, 0.6), 0 0 25px rgba(0, 229, 255, 0.4);
transform: scale(1.05);
color: #00172e;
}
</style>
.admin-actions {
display: flex;
flex-direction: column;
gap: 1rem;
margin-top: 1rem;
}
.admin-card {
display: block;
background-color: rgba(0, 229, 255, 0.1);
padding: 1rem 1.5rem;
border-radius: 12px;
color: #00e5ff;
text-decoration: none;
font-weight: bold;
transition: all 0.3s ease;
box-shadow: 0 4px 12px rgba(0, 229, 255, 0.05);
}
.admin-card:hover {
background-color: rgba(0, 229, 255, 0.25);
transform: translateY(-2px);
box-shadow: 0 6px 18px rgba(0, 229, 255, 0.15);
}
.admin-card.disabled {
opacity: 0.4;
pointer-events: none;
cursor: default;
}
.admin-actions {
text-align: left;
margin: 1.5rem 2rem;
}
.btn-create {
display: inline-block;
padding: 0.6rem 1.2rem;
font-size: 1rem;
background-color: #00e5ff;
color: #0d1117;
border: none;
border-radius: 10px;
font-weight: bold;
text-decoration: none;
box-shadow: 0 4px 10px rgba(0, 229, 255, 0.2);
transition: background-color 0.3s, transform 0.2s;
}
.btn-create:hover {
background-color: #00bcd4;
transform: translateY(-2px);
}
@@ -0,0 +1,264 @@
/* === TechTacular === Jeopardy-Board, Farben über zentrale Theme-Tokens (theme.css):
Dark = Grün-Neon, Light = heller Grund + Magenta. Feste Viewport-Höhe (kein Scrollen). */
/* Overlay-Einblendung (kam früher aus style.css). */
@keyframes fadeInUp {
0% { opacity: 0; transform: translateY(20px); }
100% { opacity: 1; transform: translateY(0); }
}
/* body bekommt Layout (Shell füllt 100vh über flex:1). Farben/Hintergrund liefert theme.css. */
body.tt-body {
height: 100vh;
min-height: 100vh;
overflow: hidden;
display: flex;
flex-direction: column;
color: var(--text);
}
.tt-shell {
flex: 1;
min-height: 0;
display: flex;
flex-direction: column;
padding: 0.6rem 0.85rem;
gap: 0.55rem;
}
/* --- Kopf + Leiste --- */
.tt-header {
flex: 0 0 auto;
display: flex;
align-items: center;
justify-content: space-between;
padding: 0.5rem 1.1rem;
background-color: var(--surface);
border: 1px solid var(--border);
border-radius: 12px;
box-shadow: var(--g-soft), 0 0 8px var(--glow-w);
}
.tt-header-tools {
display: flex;
align-items: center;
gap: 0.7rem;
}
.tt-title { font-size: 1.3rem; color: var(--accent); margin: 0; text-shadow: 0 0 8px var(--glow-s); }
.tt-back, .tt-logout { text-decoration: none; font-weight: bold; }
.tt-back { color: var(--accent); }
.tt-logout { color: var(--danger); }
.tt-bar {
flex: 0 0 auto;
display: flex;
align-items: center;
justify-content: space-between;
flex-wrap: wrap;
gap: 0.55rem 0.85rem;
}
.tt-bar-group { display: flex; align-items: center; flex-wrap: wrap; gap: 0.5rem; }
.tt-btn {
padding: 0.5rem 1.1rem;
border: 0;
border-radius: 8px;
background: var(--accent);
color: var(--accent-ink);
font-weight: 700;
font-size: 0.95rem;
cursor: pointer;
text-decoration: none;
display: inline-block;
box-shadow: 0 0 14px var(--glow-w);
transition: filter 0.25s ease, transform 0.15s ease, background-color 0.25s ease;
}
.tt-btn:hover { filter: brightness(1.08); transform: translateY(-2px); }
.tt-btn[hidden] { display: none; }
.tt-btn-secondary {
background: var(--surface-2);
border: 1px solid var(--border-accent);
color: var(--text);
box-shadow: none;
}
.tt-btn-cancel {
background: rgba(255, 107, 107, 0.14);
border: 1px solid rgba(255, 107, 107, 0.55);
color: var(--danger);
box-shadow: none;
}
.tt-btn-cancel:hover { background: rgba(255, 107, 107, 0.28); color: #fff; }
.tt-hud { gap: 0.4rem; }
.tt-stat {
display: inline-flex;
align-items: baseline;
gap: 0.4rem;
padding: 0.35rem 0.7rem;
background: var(--surface-2);
border: 1px solid var(--border);
border-radius: 10px;
font-size: 0.72rem;
text-transform: uppercase;
letter-spacing: 0.05em;
color: var(--muted);
white-space: nowrap;
}
.tt-stat b { font-size: 1.05rem; color: var(--accent); }
/* --- Board --- */
.tt-stage {
flex: 1;
min-height: 0;
display: flex;
justify-content: center;
overflow: hidden;
}
.tt-board {
display: grid;
gap: clamp(0.3rem, 1vmin, 0.7rem);
width: 100%;
height: 100%;
min-height: 0;
/* grid-template-columns wird per JS gesetzt (eine Spalte je Kategorie) */
}
.tt-col {
display: flex;
flex-direction: column;
gap: clamp(0.3rem, 1vmin, 0.7rem);
min-height: 0;
}
.tt-cat-title {
flex: 0 0 auto;
display: flex;
align-items: center;
justify-content: center;
text-align: center;
padding: 0.5rem 0.4rem;
background: var(--surface-2);
border: 1px solid var(--border-accent);
border-radius: 8px;
color: var(--accent);
font-weight: 800;
font-size: clamp(0.7rem, 1.1vw, 0.95rem);
line-height: 1.15;
hyphens: auto;
}
.tt-tile {
flex: 1;
min-height: 0;
display: flex;
align-items: center;
justify-content: center;
border: 1px solid var(--border-accent);
border-radius: 8px;
background: linear-gradient(145deg, var(--surface), var(--surface-2));
color: var(--accent);
font-weight: 800;
font-size: clamp(1rem, 2.2vw, 1.8rem);
cursor: pointer;
transition: transform 0.12s ease, box-shadow 0.2s ease, border-color 0.2s ease;
}
.tt-tile:hover:not(.answered) {
border-color: var(--accent);
box-shadow: 0 0 14px var(--glow-s), inset 0 0 18px var(--glow-w);
transform: translateY(-2px);
}
.tt-tile.answered {
cursor: default;
font-size: clamp(1.2rem, 3vw, 2rem);
}
.tt-tile.answered.correct { border-color: #00ff88; color: #00ff88; background: rgba(0, 255, 136, 0.08); }
.tt-tile.answered.wrong { border-color: #ff6b6b; color: #ff6b6b; background: rgba(255, 107, 107, 0.08); }
/* --- Overlays --- */
.tt-overlay {
position: fixed;
inset: 0;
display: flex;
align-items: center;
justify-content: center;
background: var(--bg-glow), rgba(0, 0, 0, 0.55);
backdrop-filter: blur(4px);
z-index: 1000;
padding: 1rem;
}
.tt-overlay[hidden] { display: none; }
.tt-q-card, .tt-result-card {
background: var(--surface);
border: 1px solid var(--border-accent);
border-radius: 16px;
padding: 1.5rem 1.8rem;
width: min(640px, 94vw);
max-height: 90vh;
overflow-y: auto;
box-shadow: 0 0 30px var(--glow-w);
animation: fadeInUp 0.4s ease-out;
}
.tt-q-head {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 0.6rem;
}
.tt-q-cat { color: var(--muted); font-weight: 700; text-transform: uppercase; letter-spacing: 0.06em; font-size: 0.85rem; }
.tt-q-points { color: var(--accent); font-weight: 800; font-size: 1.3rem; }
.tt-q-instruction { color: var(--muted); font-size: 0.85rem; font-weight: 700; margin-bottom: 0.35rem; }
.tt-q-text {
color: var(--heading); font-size: 1.3rem; margin-bottom: 1.1rem; line-height: 1.4;
border-left: 3px solid var(--accent); padding-left: 0.75rem; font-style: italic;
}
.tt-q-answers { display: grid; gap: 0.6rem; }
.tt-answer {
text-align: left;
padding: 0.75rem 1rem;
border: 1px solid var(--border-accent);
border-radius: 10px;
background: var(--surface-2);
color: var(--text);
font-size: 1rem;
cursor: pointer;
transition: border-color 0.2s ease, background 0.2s ease;
}
.tt-answer:hover:not(:disabled) { border-color: var(--accent); background: var(--surface); }
.tt-answer:disabled { cursor: default; }
.tt-answer.correct { border-color: #00ff88; background: rgba(0, 255, 136, 0.12); color: #b8ffdc; }
.tt-answer.wrong { border-color: #ff6b6b; background: rgba(255, 107, 107, 0.12); color: #ffd0d0; }
.tt-q-feedback { margin-top: 0.9rem; font-weight: 700; min-height: 1.2rem; }
.tt-q-feedback.correct { color: #00ff88; }
.tt-q-feedback.wrong { color: #ff6b6b; }
.tt-q-actions { display: flex; justify-content: flex-end; margin-top: 1rem; }
.tt-result-card { text-align: center; width: min(440px, 94vw); }
.tt-result-card h2 { color: var(--accent); margin-bottom: 0.6rem; }
.tt-result-score { font-size: 1.4rem; margin-bottom: 0.4rem; color: var(--text); }
.tt-result-score strong { color: var(--accent); }
.tt-result-detail { color: var(--muted); margin-bottom: 0.6rem; }
.tt-result-high { color: #00ff88; font-weight: 800; margin-bottom: 1rem; }
.tt-result-high[hidden] { display: none; }
.tt-result-actions { display: flex; flex-wrap: wrap; gap: 0.75rem; justify-content: center; margin-top: 1rem; }
.tt-idle { margin: auto; color: var(--muted); text-align: center; padding: 2rem 1rem; }
@media (max-width: 600px) {
.tt-title { font-size: 1.15rem; }
.tt-stat { font-size: 0.62rem; padding: 0.3rem 0.5rem; }
.tt-q-text { font-size: 1.05rem; }
}
+170
View File
@@ -0,0 +1,170 @@
/* ============================================================
MINDFLUX THEME – zentrale Design-Tokens + Komponenten
Dark = Grün-Neon | Light = heller Grund + Magenta-Glow
Umschaltung über <html data-theme="dark|light"> (siehe theme.js)
============================================================ */
:root, [data-theme="dark"] {
--bg:#06090a; --bg-glow: radial-gradient(900px 420px at 60% -10%, rgba(43,217,106,.10), transparent 60%);
--panel:#0c1110; --panel-2:#0e1513; --surface:#0b100e; --surface-2:#101713;
--border:#1a2520; --line:#16201b;
--border-accent:rgba(43,217,106,.45); --accent:#2bd96a; --accent-2:#6ef58f; --accent-ink:#04140a;
--text:#d7e0d9; --muted:#717c74; --heading:#ffffff; --danger:#ff5f6b;
--glow-s:rgba(43,217,106,.55); --glow-w:rgba(43,217,106,.16);
--g-soft:0 0 18px var(--glow-w);
}
[data-theme="light"] {
--bg:#f4eef3; --bg-glow: radial-gradient(900px 420px at 60% -10%, rgba(209,29,146,.10), transparent 60%);
--panel:#ffffff; --panel-2:#fbf6fa; --surface:#ffffff; --surface-2:#faf4f9;
--border:#e9dee8; --line:#efe6ee;
--border-accent:rgba(209,29,146,.40); --accent:#d11d92; --accent-2:#ff5bc0; --accent-ink:#ffffff;
--text:#3c2c39; --muted:#8a7d88; --heading:#1b1019; --danger:#d12942;
--glow-s:rgba(209,29,146,.40); --glow-w:rgba(209,29,146,.12);
--g-soft:0 6px 18px var(--glow-w);
}
* { box-sizing:border-box; margin:0; padding:0; }
html,body { height:100%; }
body {
font-family:"Inter","Segoe UI",system-ui,-apple-system,Roboto,sans-serif;
background:var(--bg-glow), var(--bg); color:var(--text);
min-height:100vh; transition:background-color .35s ease,color .35s ease;
}
a { color:var(--accent); }
::-webkit-scrollbar{width:10px;height:10px} ::-webkit-scrollbar-thumb{background:var(--line);border-radius:9px}
/* ===== App-Shell (Sidebar | Mitte | rechte Spalte) ===== */
.mf-shell { display:grid; grid-template-columns:264px 1fr 332px; grid-template-rows:auto 1fr; min-height:100vh; }
.mf-shell.no-right { grid-template-columns:264px 1fr; }
.mf-sidebar { grid-column:1; grid-row:1 / 3; background:var(--panel); border-right:1px solid var(--border); padding:1.2rem 1rem; display:flex; flex-direction:column; gap:1.1rem; }
.mf-topbar { grid-column:2 / 4; grid-row:1; display:flex; align-items:flex-start; gap:1rem; padding:1.4rem 1.6rem 0; }
.mf-shell.no-right .mf-topbar { grid-column:2; }
.mf-main { grid-column:2; grid-row:2; padding:1.3rem 1.2rem 1.6rem 1.6rem; min-width:0; }
.mf-rightbar { grid-column:3; grid-row:2; padding:1.3rem 1.6rem 1.6rem 0; display:flex; flex-direction:column; gap:1rem; }
/* ===== Logo ===== */
.mf-logo { display:flex; align-items:center; gap:.6rem; padding:.2rem .3rem .4rem; text-decoration:none; }
.mf-logo .mark { width:38px; height:38px; flex:0 0 auto; background:var(--accent);
-webkit-mask:url("/img/mindflux-emblem.png") center/contain no-repeat; mask:url("/img/mindflux-emblem.png") center/contain no-repeat;
filter:drop-shadow(0 0 8px var(--glow-s)); }
.mf-logo .txt b { color:var(--accent); font-weight:800; letter-spacing:.13em; font-size:1.02rem; display:block; text-shadow:0 0 12px var(--glow-s); }
.mf-logo .txt span { color:var(--muted); font-size:.56rem; letter-spacing:.22em; }
/* ===== Sidebar-Navigation ===== */
.mf-nav { display:flex; flex-direction:column; gap:.25rem; }
.mf-nav a { display:flex; align-items:center; gap:.75rem; padding:.7rem .85rem; border-radius:11px; color:var(--muted); text-decoration:none; font-size:.9rem; font-weight:600; border:1px solid transparent; transition:all .18s ease; }
.mf-nav a:hover { color:var(--text); background:var(--surface-2); }
.mf-nav a.active { color:var(--accent-ink); background:linear-gradient(100deg,var(--accent),var(--accent-2)); box-shadow:0 0 20px var(--glow-s); }
.mf-nav a.active svg { color:var(--accent-ink); }
.mf-nav svg { width:18px; height:18px; color:var(--accent); flex:0 0 auto; }
/* ===== Profil / Level / Streak ===== */
.mf-profile { border:1px solid var(--border); border-radius:13px; padding:.7rem; background:var(--surface); }
.mf-profile .row { display:flex; align-items:center; gap:.6rem; }
.mf-avatar { width:38px; height:38px; border-radius:50%; background:linear-gradient(135deg,var(--accent),var(--accent-2)); display:inline-flex; align-items:center; justify-content:center; color:var(--accent-ink); font-weight:800; box-shadow:0 0 14px var(--glow-s); overflow:hidden; }
.mf-avatar img { width:100%; height:100%; object-fit:cover; }
.mf-profile b { color:var(--heading); font-size:.86rem; display:block; }
.mf-profile .role { color:var(--accent); font-size:.72rem; }
.mf-meta { font-size:.74rem; }
.mf-meta .lvl { color:var(--muted); letter-spacing:.04em; } .mf-meta .lvl b { color:var(--heading); }
.mf-meta .xp { color:var(--muted); margin:.2rem 0 .35rem; }
.mf-streak { display:flex; align-items:center; gap:.55rem; margin-top:.2rem; }
.mf-streak .fire { font-size:1.1rem; filter:drop-shadow(0 0 6px var(--glow-s)); }
.mf-streak b { color:var(--heading); font-size:.82rem; display:block; } .mf-streak small { color:var(--muted); }
.mf-brain { margin-top:auto; opacity:.55; display:flex; justify-content:center; filter:drop-shadow(0 0 10px var(--glow-s)); }
.mf-brain svg { width:150px; height:auto; }
/* ===== Topbar ===== */
.mf-hello h1 { color:var(--heading); font-size:1.85rem; font-weight:800; letter-spacing:-.01em; }
.mf-hello h1 .nm { color:var(--accent); text-shadow:0 0 16px var(--glow-s); }
.mf-hello p { color:var(--muted); margin-top:.35rem; font-size:.95rem; }
.mf-pulse { flex:1; min-width:0; display:flex; justify-content:center; align-items:center; }
.mf-pulse svg { width:200px; max-width:100%; filter:drop-shadow(0 0 7px var(--glow-s)); }
.mf-tools { display:flex; align-items:center; gap:.6rem; margin-left:auto; }
.mf-iconbtn { width:38px; height:38px; border-radius:10px; border:1px solid var(--border); background:var(--surface); color:var(--muted); display:inline-flex; align-items:center; justify-content:center; cursor:pointer; text-decoration:none; transition:all .18s; }
.mf-iconbtn:hover { color:var(--accent); border-color:var(--border-accent); box-shadow:0 0 14px var(--glow-w); }
.mf-iconbtn svg { width:18px; height:18px; }
.mf-search { display:flex; align-items:center; gap:.5rem; background:var(--surface); border:1px solid var(--border); border-radius:10px; padding:.5rem .8rem; color:var(--muted); }
.mf-search input { background:none; border:0; outline:none; color:var(--text); font-size:.86rem; width:130px; }
.mf-search svg { width:15px; height:15px; }
/* ===== Theme-Umschalter ===== */
.mf-theme { width:42px; height:38px; border-radius:50%; border:1px solid var(--border-accent); background:var(--surface); cursor:pointer; display:inline-flex; align-items:center; justify-content:center; color:var(--accent); box-shadow:0 0 14px var(--glow-w); }
.mf-theme svg { width:18px; height:18px; }
/* ===== HUD-Spielkarten ===== */
.mf-grid { display:grid; grid-template-columns:repeat(3,1fr); gap:1.1rem; }
.mf-card { position:relative; display:flex; flex-direction:column; padding:1.15rem 1.2rem 1.1rem; background:var(--surface);
border:1px solid var(--border-accent); --n:18px;
clip-path:polygon(0 0, calc(100% - var(--n)) 0, 100% var(--n), 100% 100%, 0 100%);
text-decoration:none; color:inherit; filter:drop-shadow(0 0 7px var(--glow-w)); transition:transform .16s ease, filter .25s ease, background-color .2s; }
.mf-card::before { content:""; position:absolute; left:10px; top:10px; width:14px; height:14px; border-left:2px solid var(--accent); border-top:2px solid var(--accent); opacity:.7; }
.mf-card:hover { transform:translateY(-4px); background:var(--surface-2); filter:drop-shadow(0 0 16px var(--glow-s)); }
.mf-card .ico { width:58px; height:58px; color:var(--accent); margin-bottom:.7rem; filter:drop-shadow(0 0 6px var(--glow-s)); }
.mf-card .ico svg { width:100%; height:100%; }
.mf-card h3 { color:var(--heading); font-size:1.06rem; font-weight:700; margin-bottom:.4rem; }
.mf-card p { color:var(--muted); font-size:.83rem; line-height:1.5; flex:1; }
.mf-play { margin-top:.9rem; align-self:flex-start; display:inline-flex; align-items:center; gap:.45rem; font-size:.74rem; font-weight:800; letter-spacing:.08em; color:var(--accent); border:1px solid var(--border-accent); border-radius:8px; padding:.5rem .85rem; text-decoration:none; transition:all .18s; }
.mf-card:hover .mf-play { background:var(--accent); color:var(--accent-ink); box-shadow:0 0 16px var(--glow-s); }
.mf-play svg { width:14px; height:14px; }
/* ===== Panels / Widgets ===== */
.mf-panel { background:var(--surface); border:1px solid var(--border); border-radius:14px; padding:1.1rem; box-shadow:var(--g-soft); }
.mf-panel.accent { border-color:var(--border-accent); box-shadow:0 0 20px var(--glow-w); }
.mf-panel h4 { display:flex; align-items:center; gap:.5rem; color:var(--accent); font-size:.74rem; letter-spacing:.12em; text-transform:uppercase; margin-bottom:.9rem; }
.mf-panel h4 svg { width:15px; height:15px; }
.mf-eyebrow { color:var(--accent); font-weight:700; text-transform:uppercase; letter-spacing:.08em; font-size:.8rem; }
.mf-bar { height:7px; border-radius:99px; background:var(--surface-2); border:1px solid var(--border); overflow:hidden; }
.mf-bar > i { display:block; height:100%; background:linear-gradient(90deg,var(--accent),var(--accent-2)); box-shadow:0 0 10px var(--glow-s); }
/* ===== Buttons ===== */
.mf-btn { display:inline-flex; align-items:center; justify-content:center; gap:.45rem; font-weight:800; font-size:.82rem; letter-spacing:.04em; border:0; border-radius:9px; padding:.6rem 1.1rem; cursor:pointer; text-decoration:none; background:var(--accent); color:var(--accent-ink); box-shadow:0 0 18px var(--glow-s); transition:all .18s; }
.mf-btn:hover { filter:brightness(1.05); transform:translateY(-1px); }
.mf-btn svg { width:15px; height:15px; }
.mf-btn.outline { background:transparent; color:var(--accent); border:1px solid var(--border-accent); box-shadow:none; }
.mf-btn.outline:hover { background:var(--surface-2); }
.mf-btn.ghost { background:var(--surface-2); color:var(--text); border:1px solid var(--border); box-shadow:none; }
.mf-btn.danger { background:var(--danger); color:#fff; box-shadow:none; }
/* ===== Formulare ===== */
.mf-field { display:flex; flex-direction:column; gap:.35rem; margin-bottom:.9rem; }
.mf-label { color:var(--accent); font-weight:700; font-size:.82rem; }
.mf-input, .mf-select, input.mf-input, select.mf-select, textarea.mf-input {
width:100%; padding:.65rem .8rem; border-radius:10px; border:1px solid var(--border);
background:var(--surface-2); color:var(--text); font-size:.95rem; font-family:inherit; }
.mf-input:focus, .mf-select:focus { outline:none; border-color:var(--accent); box-shadow:0 0 0 3px var(--glow-w); }
.mf-input::placeholder { color:var(--muted); }
/* ===== Tabellen ===== */
.mf-table { width:100%; border-collapse:collapse; }
.mf-table th, .mf-table td { text-align:left; padding:.7rem .8rem; border-bottom:1px solid var(--border); font-size:.9rem; }
.mf-table th { color:var(--accent); text-transform:uppercase; font-size:.72rem; letter-spacing:.08em; }
.mf-table tr:hover td { background:var(--surface-2); }
/* ===== Badges ===== */
.mf-badge { font-size:.68rem; text-transform:uppercase; letter-spacing:.05em; padding:.18rem .5rem; border-radius:7px; background:var(--accent-dim,rgba(43,217,106,.12)); color:var(--accent); border:1px solid var(--border-accent); }
/* ===== Standalone-Karte (Login/Auth, einzelne Inhaltsseiten) ===== */
.mf-center { display:flex; align-items:center; justify-content:center; min-height:100vh; padding:1.5rem; }
.mf-cardbox { width:100%; max-width:420px; background:var(--surface); border:1px solid var(--border-accent); border-radius:18px; padding:2rem; box-shadow:0 0 30px var(--glow-w); }
.mf-container { max-width:1000px; margin:0 auto; padding:1.5rem; }
.mf-page-head { display:flex; align-items:center; gap:1rem; margin-bottom:1.4rem; }
.mf-back { color:var(--accent); text-decoration:none; font-weight:700; font-size:.88rem; }
/* schwebender Theme-Umschalter für Seiten ohne Topbar */
.mf-theme-float { position:fixed; top:16px; right:16px; z-index:1000; }
/* ===== Fußzeile (Support / AGB / Impressum …) ===== */
.mf-footer {
display:flex; flex-wrap:wrap; justify-content:center; align-items:center;
gap:.35rem 1rem; padding:1.1rem 1.5rem;
border-top:1px solid var(--border); background:var(--panel);
font-size:.82rem; color:var(--muted);
}
.mf-footer a { color:var(--muted); text-decoration:none; position:relative; }
.mf-footer a:hover { color:var(--accent); }
.mf-footer a + a::before { content:"·"; position:absolute; left:-.6rem; color:var(--border); }
@media (max-width:1180px){ .mf-shell{grid-template-columns:240px 1fr;} .mf-rightbar{display:none;} .mf-topbar{grid-column:2;} .mf-main{grid-column:2;} }
@media (max-width:820px){ .mf-shell{grid-template-columns:1fr;} .mf-sidebar{display:none;} .mf-topbar,.mf-main{grid-column:1;} .mf-grid{grid-template-columns:repeat(2,1fr);} }
@media (max-width:560px){ .mf-grid{grid-template-columns:1fr;} }
@@ -0,0 +1,73 @@
<!DOCTYPE html>
<html lang="de" data-theme="dark">
<head>
<meta charset="UTF-8">
<title>Datenschutz - FinalFlux AP1</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="/css/style.css">
<link rel="stylesheet" href="/css/theme.css">
<link rel="stylesheet" href="/css/finalflux.css">
<script src="/js/theme.js"></script>
</head>
<body class="finalflux-page">
<div class="mf-theme-float"><button class="mf-theme"></button></div>
<main>
<a href="/finalflux" class="back-link">Zurück zu FinalFlux</a>
<h1>Datenschutz & Datensicherheit</h1>
<section>
<h2>Prüfungsmodus</h2>
<p>
Dieser FluxCheck trainiert Datenschutz so, wie er in AP1-Handlungssituationen
auftaucht: personenbezogene Daten erkennen, DSGVO-Grundsätze anwenden,
Betroffenenrechte einordnen, Schutzmaßnahmen auswählen und Praxisfälle bewerten.
</p>
</section>
<section>
<h2>Merksatz</h2>
<p>
Datenschutz schützt Menschen hinter den Daten. Datensicherheit schützt die Daten
technisch und organisatorisch. In der Prüfung musst du meistens beides zusammen denken.
</p>
</section>
<section class="finalflux-test" data-finalflux-test aria-live="polite">
<div class="test-meta">
<span data-question-counter>Frage 1</span>
<span data-score-counter>0 richtig</span>
</div>
<div class="category-block">
<p class="eyebrow">Kategorie</p>
<h2 data-category-title>Datenschutz</h2>
<p data-category-hint>Personenbezogene Daten, Rechte und Schutzmaßnahmen.</p>
</div>
<div class="question-card">
<h3 data-question-text></h3>
<div data-answer-options class="answer-options"></div>
<div data-answer-feedback class="fluxcheck-result"></div>
</div>
<div class="test-actions">
<button type="button" data-check-answer>Antwort prüfen</button>
<button type="button" data-skip-question class="secondary">Überspringen</button>
<button type="button" data-next-question class="secondary" disabled>Weiter</button>
</div>
</section>
<section data-test-result class="finalflux-panel" hidden>
<h2>Auswertung</h2>
<p data-result-summary></p>
<ul data-category-summary class="key-list"></ul>
<div class="finalflux-actions">
<button type="button" data-restart-test>Test neu starten</button>
<a href="/finalflux">Zurück zur Übersicht</a>
</div>
</section>
</main>
<script src="/js/finalflux-test.js" data-questions-src="/finalflux/questions/datenschutz.json" defer></script>
</body>
</html>
@@ -0,0 +1,68 @@
<!DOCTYPE html>
<html lang="de" data-theme="dark">
<head>
<meta charset="UTF-8">
<title>IP-Adressberechnung - FinalFlux AP1</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="/css/style.css">
<link rel="stylesheet" href="/css/theme.css">
<link rel="stylesheet" href="/css/finalflux.css">
<script src="/js/theme.js"></script>
</head>
<body class="finalflux-page">
<div class="mf-theme-float"><button class="mf-theme"></button></div>
<main>
<a href="/finalflux" class="back-link">Zurück zu FinalFlux</a>
<h1>IP-Adressberechnung</h1>
<section>
<h2>Lernfokus</h2>
<p>Trainiere IPv4, CIDR, Netzadresse, Broadcast und Hostanzahlen.</p>
<ul class="key-list">
<li>CIDR und Subnetzmaske zusammenbringen.</li>
<li>Netzadresse, Broadcast und Hostbereich bestimmen.</li>
<li>Typische Subnetting-Fehler vermeiden.</li>
</ul>
</section>
<section>
<h2>Prüfungsmodus</h2>
<p>Dieser FluxCheck führt dich durch die wichtigsten AP1-Aspekte dieses Themas. Du kannst Antworten prüfen, Fragen überspringen und bekommst am Ende eine Auswertung nach Kategorie.</p>
</section>
<section class="finalflux-test" data-finalflux-test aria-live="polite">
<div class="test-meta">
<span data-question-counter>Frage 1</span>
<span data-score-counter>0 richtig</span>
</div>
<div class="category-block">
<p class="eyebrow">Kategorie</p>
<h2 data-category-title>IP-Adressberechnung</h2>
<p data-category-hint>AP1-Training</p>
</div>
<div class="question-card">
<h3 data-question-text></h3>
<div data-answer-options class="answer-options"></div>
<div data-answer-feedback class="fluxcheck-result"></div>
</div>
<div class="test-actions">
<button type="button" data-check-answer>Antwort prüfen</button>
<button type="button" data-skip-question class="secondary">Überspringen</button>
<button type="button" data-next-question class="secondary" disabled>Weiter</button>
</div>
</section>
<section data-test-result class="finalflux-panel" hidden>
<h2>Auswertung</h2>
<p data-result-summary></p>
<ul data-category-summary class="key-list"></ul>
<div class="finalflux-actions">
<button type="button" data-restart-test>Test neu starten</button>
<a href="/finalflux">Zurück zur Übersicht</a>
</div>
</section>
</main>
<script src="/js/finalflux-test.js" data-questions-src="/finalflux/questions/ap1_ip-berechnung.json" defer></script>
</body>
</html>
@@ -0,0 +1,66 @@
<!DOCTYPE html>
<html lang="de" data-theme="dark">
<head>
<meta charset="UTF-8">
<title>Projektmanagement - FinalFlux AP1</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="/css/style.css">
<link rel="stylesheet" href="/css/theme.css">
<link rel="stylesheet" href="/css/finalflux.css">
<script src="/js/theme.js"></script>
</head>
<body class="finalflux-page">
<div class="mf-theme-float"><button class="mf-theme"></button></div>
<main>
<a href="/finalflux" class="back-link">Zurück zu FinalFlux</a>
<h1>Projektmanagement in der AP1</h1>
<section>
<h2>Prüfungsmodus</h2>
<p>
Dieser FluxCheck führt dich durch prüfungsrelevante Projektmanagement-Themen:
Auftrag, Ziele, Anforderungen, Planung, Risiken, Qualität, Kommunikation,
Dokumentation und Abnahme. Jede Frage gehört zu einer Kategorie, die oben im
Themenblock angezeigt wird.
</p>
</section>
<section class="finalflux-test" data-finalflux-test aria-live="polite">
<div class="test-meta">
<span data-question-counter>Frage 1</span>
<span data-score-counter>0 richtig</span>
</div>
<div class="category-block">
<p class="eyebrow">Kategorie</p>
<h2 data-category-title>Projektstart</h2>
<p data-category-hint>Auftrag, Ausgangslage und Ziel verstehen.</p>
</div>
<div class="question-card">
<h3 data-question-text></h3>
<div data-answer-options class="answer-options"></div>
<div data-answer-feedback class="fluxcheck-result"></div>
</div>
<div class="test-actions">
<button type="button" data-check-answer>Antwort prüfen</button>
<button type="button" data-skip-question class="secondary">Überspringen</button>
<button type="button" data-next-question class="secondary" disabled>Weiter</button>
</div>
</section>
<section data-test-result class="finalflux-panel" hidden>
<h2>Auswertung</h2>
<p data-result-summary></p>
<ul data-category-summary class="key-list"></ul>
<div class="finalflux-actions">
<button type="button" data-restart-test>Test neu starten</button>
<a href="/finalflux">Zurück zur Übersicht</a>
</div>
</section>
</main>
<script src="/js/finalflux-test.js" data-questions-src="/finalflux/questions/projektmanagement.json" defer></script>
</body>
</html>
@@ -0,0 +1,68 @@
<!DOCTYPE html>
<html lang="de" data-theme="dark">
<head>
<meta charset="UTF-8">
<title>Zahlensysteme & Speicher - FinalFlux AP1</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="/css/style.css">
<link rel="stylesheet" href="/css/theme.css">
<link rel="stylesheet" href="/css/finalflux.css">
<script src="/js/theme.js"></script>
</head>
<body class="finalflux-page">
<div class="mf-theme-float"><button class="mf-theme"></button></div>
<main>
<a href="/finalflux" class="back-link">Zurück zu FinalFlux</a>
<h1>Zahlensysteme & Speicher</h1>
<section>
<h2>Lernfokus</h2>
<p>Trainiere Binär-, Dezimal- und Hexadezimalumrechnung sowie Speichereinheiten für typische AP1-Rechenaufgaben.</p>
<ul class="key-list">
<li>Binär, Dezimal und Hexadezimal sicher unterscheiden.</li>
<li>Bit, Byte, KiB, MiB und GiB sauber umrechnen.</li>
<li>Rechenwege nachvollziehbar dokumentieren.</li>
</ul>
</section>
<section>
<h2>Prüfungsmodus</h2>
<p>Dieser FluxCheck führt dich durch die wichtigsten AP1-Aspekte dieses Themas. Du kannst Antworten prüfen, Fragen überspringen und bekommst am Ende eine Auswertung nach Kategorie.</p>
</section>
<section class="finalflux-test" data-finalflux-test aria-live="polite">
<div class="test-meta">
<span data-question-counter>Frage 1</span>
<span data-score-counter>0 richtig</span>
</div>
<div class="category-block">
<p class="eyebrow">Kategorie</p>
<h2 data-category-title>Zahlensysteme & Speicher</h2>
<p data-category-hint>AP1-Training</p>
</div>
<div class="question-card">
<h3 data-question-text></h3>
<div data-answer-options class="answer-options"></div>
<div data-answer-feedback class="fluxcheck-result"></div>
</div>
<div class="test-actions">
<button type="button" data-check-answer>Antwort prüfen</button>
<button type="button" data-skip-question class="secondary">Überspringen</button>
<button type="button" data-next-question class="secondary" disabled>Weiter</button>
</div>
</section>
<section data-test-result class="finalflux-panel" hidden>
<h2>Auswertung</h2>
<p data-result-summary></p>
<ul data-category-summary class="key-list"></ul>
<div class="finalflux-actions">
<button type="button" data-restart-test>Test neu starten</button>
<a href="/finalflux">Zurück zur Übersicht</a>
</div>
</section>
</main>
<script src="/js/finalflux-test.js" data-questions-src="/finalflux/questions/ap1_zahlensysteme.json" defer></script>
</body>
</html>
@@ -0,0 +1,365 @@
{
"title": "IP-Adressberechnung",
"questions": [
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Was beschreibt IPv4-Adresse am besten?",
"answers": [
"Sie besteht aus 4 Oktetten mit Werten von 0 bis 255.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Sie besteht aus 4 Oktetten mit Werten von 0 bis 255."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Welche Aussage zu Oktett ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Ein Oktett umfasst 8 Bit.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Ein Oktett umfasst 8 Bit."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Woran erkennst du Subnetzmaske in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Sie trennt Netz- und Hostanteil."
],
"correct": 2,
"explanation": "Sie trennt Netz- und Hostanteil."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Was ist bei CIDR besonders wichtig?",
"answers": [
"CIDR gibt die Anzahl der Netzbits an.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "CIDR gibt die Anzahl der Netzbits an."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Was beschreibt /24 am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"/24 entspricht häufig 255.255.255.0.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "/24 entspricht häufig 255.255.255.0."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Welche Aussage zu Netzanteil ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Der Netzanteil identifiziert das Subnetz."
],
"correct": 2,
"explanation": "Der Netzanteil identifiziert das Subnetz."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Woran erkennst du Hostanteil in einer AP1-Aufgabe?",
"answers": [
"Der Hostanteil identifiziert Geräte im Subnetz.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Der Hostanteil identifiziert Geräte im Subnetz."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Was ist bei private IPv4-Bereiche besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Sie werden intern genutzt, etwa 192.168.0.0/16.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Sie werden intern genutzt, etwa 192.168.0.0/16."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Was beschreibt Standardgateway am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Es verbindet das lokale Netz mit anderen Netzen."
],
"correct": 2,
"explanation": "Es verbindet das lokale Netz mit anderen Netzen."
},
{
"category": "IPv4-Grundlagen",
"hint": "Adressaufbau, Oktette und Masken verstehen.",
"text": "Welche Aussage zu APIPA ist richtig?",
"answers": [
"169.254.x.x deutet oft auf DHCP-Probleme hin.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "169.254.x.x deutet oft auf DHCP-Probleme hin."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Was beschreibt Netzadresse am besten?",
"answers": [
"Sie ist die erste Adresse eines Subnetzes.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Sie ist die erste Adresse eines Subnetzes."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Welche Aussage zu Broadcast-Adresse ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Sie ist die letzte Adresse eines klassischen IPv4-Subnetzes.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Sie ist die letzte Adresse eines klassischen IPv4-Subnetzes."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Woran erkennst du Hostanzahl in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Bei normalen Subnetzen gilt 2 hoch Hostbits minus 2."
],
"correct": 2,
"explanation": "Bei normalen Subnetzen gilt 2 hoch Hostbits minus 2."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Was ist bei /26 besonders wichtig?",
"answers": [
"/26 hat 64 Adressen pro Subnetz.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "/26 hat 64 Adressen pro Subnetz."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Was beschreibt /30 am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"/30 wird oft für Punkt-zu-Punkt-Netze genutzt.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "/30 wird oft für Punkt-zu-Punkt-Netze genutzt."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Welche Aussage zu Blockgröße ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Sie ergibt sich aus der Schrittweite im relevanten Oktett."
],
"correct": 2,
"explanation": "Sie ergibt sich aus der Schrittweite im relevanten Oktett."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Woran erkennst du Hostbits in einer AP1-Aufgabe?",
"answers": [
"Hostbits bestimmen die Anzahl möglicher Adressen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Hostbits bestimmen die Anzahl möglicher Adressen."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Was ist bei Netzbits besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Netzbits bestimmen die Subnetzgröße.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Netzbits bestimmen die Subnetzgröße."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Was beschreibt Subnetzgrenze am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Adressen müssen zur richtigen Blockgrenze gehören."
],
"correct": 2,
"explanation": "Adressen müssen zur richtigen Blockgrenze gehören."
},
{
"category": "Subnetting",
"hint": "Netz, Broadcast und Hostanzahl berechnen.",
"text": "Welche Aussage zu Broadcast nicht vergeben ist richtig?",
"answers": [
"Broadcast ist keine normale Hostadresse.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Broadcast ist keine normale Hostadresse."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Was beschreibt falsche Maske am besten?",
"answers": [
"Sie kann Hosts scheinbar in falsche Netze legen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Sie kann Hosts scheinbar in falsche Netze legen."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Welche Aussage zu falsches Gateway ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Dann sind andere Netze oft nicht erreichbar.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Dann sind andere Netze oft nicht erreichbar."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Woran erkennst du DHCP-Problem in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Fehlende automatische Adresse kann auf DHCP hindeuten."
],
"correct": 2,
"explanation": "Fehlende automatische Adresse kann auf DHCP hindeuten."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Was ist bei Doppelvergabe besonders wichtig?",
"answers": [
"Gleiche IP auf zwei Hosts verursacht Konflikte.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Gleiche IP auf zwei Hosts verursacht Konflikte."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Was beschreibt DNS vs IP am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Ping per IP, aber nicht per Name deutet auf DNS.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Ping per IP, aber nicht per Name deutet auf DNS."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Welche Aussage zu lokale Erreichbarkeit ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Erst IP, Maske und Link prüfen."
],
"correct": 2,
"explanation": "Erst IP, Maske und Link prüfen."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Woran erkennst du Routingproblem in einer AP1-Aufgabe?",
"answers": [
"Andere Netze brauchen passende Route oder Gateway.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Andere Netze brauchen passende Route oder Gateway."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Was ist bei Dokumentation besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Adresspläne verhindern Überschneidungen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Adresspläne verhindern Überschneidungen."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Was beschreibt Reservierungen am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Server und Drucker bekommen oft feste Adressen."
],
"correct": 2,
"explanation": "Server und Drucker bekommen oft feste Adressen."
},
{
"category": "Fehleranalyse IP",
"hint": "IP-Probleme in Handlungssituationen erkennen.",
"text": "Welche Aussage zu Prüfungsweg IP ist richtig?",
"answers": [
"Rechenschritte sauber notieren und Einheiten prüfen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Rechenschritte sauber notieren und Einheiten prüfen."
}
]
}
@@ -0,0 +1,365 @@
{
"title": "Zahlensysteme & Speicher",
"questions": [
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Was beschreibt Binärsystem am besten?",
"answers": [
"Es nutzt nur 0 und 1 und basiert auf Potenzen von 2.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Es nutzt nur 0 und 1 und basiert auf Potenzen von 2."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Welche Aussage zu Stellenwert ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Jede Position hat einen Wert wie 1, 2, 4, 8 oder 16.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Jede Position hat einen Wert wie 1, 2, 4, 8 oder 16."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Woran erkennst du Dezimalumrechnung in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Binärstellen werden mit ihren Zweierpotenzen addiert."
],
"correct": 2,
"explanation": "Binärstellen werden mit ihren Zweierpotenzen addiert."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Was ist bei Bit besonders wichtig?",
"answers": [
"Ein Bit ist die kleinste Informationseinheit mit 0 oder 1.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Ein Bit ist die kleinste Informationseinheit mit 0 oder 1."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Was beschreibt Nibble am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Ein Nibble besteht aus 4 Bit.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Ein Nibble besteht aus 4 Bit."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Welche Aussage zu Byte ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Ein Byte besteht aus 8 Bit."
],
"correct": 2,
"explanation": "Ein Byte besteht aus 8 Bit."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Woran erkennst du Potenzen von 2 in einer AP1-Aufgabe?",
"answers": [
"Sie sind Grundlage vieler IT-Rechenaufgaben.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Sie sind Grundlage vieler IT-Rechenaufgaben."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Was ist bei führende Nullen besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Sie ändern den Zahlenwert nicht, können aber die Darstellung auffüllen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Sie ändern den Zahlenwert nicht, können aber die Darstellung auffüllen."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Was beschreibt Dualzahl am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Eine Dualzahl ist eine Zahl im Binärsystem."
],
"correct": 2,
"explanation": "Eine Dualzahl ist eine Zahl im Binärsystem."
},
{
"category": "Binär & Dezimal",
"hint": "Stellenwerte, Potenzen und Umrechnung verstehen.",
"text": "Welche Aussage zu Prüfungsweg ist richtig?",
"answers": [
"Der Rechenweg ist oft wichtiger als nur das Endergebnis.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Der Rechenweg ist oft wichtiger als nur das Endergebnis."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Was beschreibt Hexadezimalsystem am besten?",
"answers": [
"Es nutzt Basis 16 mit Ziffern 0-9 und A-F.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Es nutzt Basis 16 mit Ziffern 0-9 und A-F."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Welche Aussage zu A bis F ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"A bis F stehen für die Werte 10 bis 15.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "A bis F stehen für die Werte 10 bis 15."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Woran erkennst du Hex zu Binär in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Eine Hexstelle entspricht genau 4 Bit."
],
"correct": 2,
"explanation": "Eine Hexstelle entspricht genau 4 Bit."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Was ist bei Binär zu Hex besonders wichtig?",
"answers": [
"Binärzahlen werden in Vierergruppen geteilt.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Binärzahlen werden in Vierergruppen geteilt."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Was beschreibt Hex FF am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"FF entspricht dezimal 255.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "FF entspricht dezimal 255."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Welche Aussage zu Hex in Adressen ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Hex wird häufig bei Speicher- und Netzwerkdarstellungen genutzt."
],
"correct": 2,
"explanation": "Hex wird häufig bei Speicher- und Netzwerkdarstellungen genutzt."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Woran erkennst du Basis 16 in einer AP1-Aufgabe?",
"answers": [
"Jede Stelle ist eine Potenz von 16.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Jede Stelle ist eine Potenz von 16."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Was ist bei 2F besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"2F bedeutet 2 mal 16 plus 15.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "2F bedeutet 2 mal 16 plus 15."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Was beschreibt BC am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"BC kann aus der Binärgruppe 1011 1100 entstehen."
],
"correct": 2,
"explanation": "BC kann aus der Binärgruppe 1011 1100 entstehen."
},
{
"category": "Hexadezimal",
"hint": "Hexwerte kompakt lesen und in Binär/Dezimal übertragen.",
"text": "Welche Aussage zu Prüfungstipp Hex ist richtig?",
"answers": [
"Vierergruppen verhindern viele Umrechnungsfehler.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Vierergruppen verhindern viele Umrechnungsfehler."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Was beschreibt kB und KiB am besten?",
"answers": [
"kB nutzt 1000, KiB nutzt 1024 Byte.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "kB nutzt 1000, KiB nutzt 1024 Byte."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Welche Aussage zu MB und MiB ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"MB ist dezimal, MiB ist binär gerechnet.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "MB ist dezimal, MiB ist binär gerechnet."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Woran erkennst du GiB in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Ein GiB entspricht 1024 hoch 3 Byte."
],
"correct": 2,
"explanation": "Ein GiB entspricht 1024 hoch 3 Byte."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Was ist bei Bit zu Byte besonders wichtig?",
"answers": [
"8 Bit ergeben 1 Byte.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "8 Bit ergeben 1 Byte."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Was beschreibt Übertragungsrate am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Bit pro Sekunde ist nicht dasselbe wie Byte pro Sekunde.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Bit pro Sekunde ist nicht dasselbe wie Byte pro Sekunde."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Welche Aussage zu Marketingangaben ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Speicherhersteller nutzen oft dezimale Einheiten."
],
"correct": 2,
"explanation": "Speicherhersteller nutzen oft dezimale Einheiten."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Woran erkennst du Betriebssystemanzeige in einer AP1-Aufgabe?",
"answers": [
"Systeme zeigen Kapazitäten häufig binärnah an.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Systeme zeigen Kapazitäten häufig binärnah an."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Was ist bei Rundung besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Rundungen müssen in Prüfungen nachvollziehbar sein.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Rundungen müssen in Prüfungen nachvollziehbar sein."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Was beschreibt Einheitenfehler am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Verwechslung von Bit und Byte ist ein klassischer Fehler."
],
"correct": 2,
"explanation": "Verwechslung von Bit und Byte ist ein klassischer Fehler."
},
{
"category": "Speichereinheiten",
"hint": "Bit, Byte und Binärpräfixe in Aufgaben sicher anwenden.",
"text": "Welche Aussage zu Rechenweg Speicher ist richtig?",
"answers": [
"Schreibe Einheitenschritte sauber auf.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Schreibe Einheitenschritte sauber auf."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "Backuparten",
"questions": [
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Was ist das Hauptziel eines Backups?",
"answers": ["Daten nach Verlust wiederherstellen können", "Daten absichtlich verlangsamen", "Passwörter öffentlich speichern"],
"correct": 0,
"explanation": "Backups dienen der Wiederherstellung nach Verlust, Fehlern oder Ausfällen."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Was bedeutet Restore?",
"answers": ["Wiederherstellung von Daten aus einer Sicherung", "Löschen aller Sicherungen", "Komprimieren eines Monitors"],
"correct": 0,
"explanation": "Restore ist das Zurückspielen gesicherter Daten."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Warum sollte ein Restore regelmäßig getestet werden?",
"answers": ["Damit sicher ist, dass die Sicherung im Ernstfall funktioniert", "Damit Backups größer werden", "Damit keine Dokumentation nötig ist"],
"correct": 0,
"explanation": "Ein Backup ist nur wertvoll, wenn die Wiederherstellung klappt."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Was ist RPO?",
"answers": ["Maximal tolerierbarer Datenverlust in Zeit", "Maximale Bildschirmauflösung", "Ein Druckerprotokoll"],
"correct": 0,
"explanation": "RPO beschreibt, wie alt die wiederhergestellten Daten höchstens sein dürfen."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Was ist RTO?",
"answers": ["Maximal tolerierbare Wiederherstellungszeit", "Router-Temperatur-Option", "Eine Dateiendung"],
"correct": 0,
"explanation": "RTO beschreibt, wie schnell ein System nach Ausfall wieder laufen muss."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Warum ist eine Backup-Dokumentation wichtig?",
"answers": ["Damit Zuständigkeiten, Zeitpunkte und Wiederherstellung nachvollziehbar sind", "Damit niemand Backups findet", "Damit Tests überflüssig sind"],
"correct": 0,
"explanation": "Dokumentation macht Sicherung und Restore planbar."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Welche Daten sollten gesichert werden?",
"answers": ["Geschäftskritische Daten und notwendige Konfigurationen", "Nur Hintergrundbilder", "Ausschließlich leere Ordner"],
"correct": 0,
"explanation": "Sicherungsumfang richtet sich nach Wiederherstellungsbedarf und Kritikalität."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Was ist ein Backup-Fenster?",
"answers": ["Zeitraum, in dem Sicherungen durchgeführt werden", "Ein Fenster im Serverraum", "Eine Monitorfunktion"],
"correct": 0,
"explanation": "Backups werden oft in Zeiten geringer Nutzung geplant."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Was ist bei personenbezogenen Daten in Backups wichtig?",
"answers": ["Schutz, Zugriff und Löschkonzept beachten", "Backups immer öffentlich machen", "Datenschutz gilt dort nie"],
"correct": 0,
"explanation": "Auch Backups können personenbezogene Daten enthalten."
},
{
"category": "Backup-Grundlagen",
"hint": "Verstehe Zweck, Begriffe und Anforderungen an Datensicherung.",
"text": "Welche Aussage ist korrekt?",
"answers": ["Backups müssen zum Risiko und Wiederherstellungsbedarf passen", "Ein Backup ersetzt jede IT-Sicherheit", "Ein einziges ungetestetes Backup reicht immer"],
"correct": 0,
"explanation": "Backup-Konzepte müssen Anforderungen, Risiken und Tests berücksichtigen."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Was sichert ein Vollbackup?",
"answers": ["Alle ausgewählten Daten", "Nur Änderungen seit gestern", "Nur gelöschte Dateien"],
"correct": 0,
"explanation": "Ein Vollbackup enthält den kompletten ausgewählten Datenbestand."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Was sichert ein differentielles Backup?",
"answers": ["Alle Änderungen seit dem letzten Vollbackup", "Nur Änderungen seit dem letzten beliebigen Backup", "Immer alle Daten"],
"correct": 0,
"explanation": "Differentiell bezieht sich auf das letzte Vollbackup."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Was sichert ein inkrementelles Backup?",
"answers": ["Änderungen seit dem letzten Backup", "Immer alle Daten", "Nur Betriebssystemdateien"],
"correct": 0,
"explanation": "Inkrementell bezieht sich auf das letzte Backup, egal ob voll oder inkrementell."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Welche Sicherungsart braucht meist am meisten Speicherplatz?",
"answers": ["Vollbackup", "Inkrementelles Backup", "Keine Sicherung"],
"correct": 0,
"explanation": "Vollbackups enthalten den gesamten ausgewählten Datenbestand."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Welche Sicherungsart spart im Alltag meist am meisten Speicherplatz?",
"answers": ["Inkrementelles Backup", "Tägliches Vollbackup", "Doppelte Vollsicherung"],
"correct": 0,
"explanation": "Inkrementelle Backups sichern nur die Änderungen seit der letzten Sicherung."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Was brauchst du beim differentiellen Restore?",
"answers": ["Letztes Vollbackup und letztes differentielles Backup", "Alle differentiellen Backups", "Nur das erste inkrementelle Backup"],
"correct": 0,
"explanation": "Differentiell enthält alle Änderungen seit dem letzten Vollbackup."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Was brauchst du beim inkrementellen Restore typischerweise?",
"answers": ["Vollbackup und alle benötigten inkrementellen Backups der Kette", "Nur das letzte inkrementelle Backup", "Kein Vollbackup"],
"correct": 0,
"explanation": "Die inkrementelle Kette muss vollständig sein."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Was ist ein Nachteil langer inkrementeller Ketten?",
"answers": ["Restore kann länger dauern und anfälliger sein", "Sie brauchen immer mehr Kabel", "Sie verhindern Datenschutz"],
"correct": 0,
"explanation": "Wenn ein Teil der Kette fehlt oder defekt ist, kann der Restore scheitern."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Welche Strategie ist häufig praktikabel?",
"answers": ["Regelmäßige Vollbackups plus tägliche inkrementelle oder differentielle Sicherungen", "Nie sichern", "Nur einmal im Jahr prüfen"],
"correct": 0,
"explanation": "Kombinationen balancieren Speicherbedarf, Sicherungsdauer und Restore-Aufwand."
},
{
"category": "Voll, differentiell, inkrementell",
"hint": "Unterscheide Sicherungsarten nach Speicherbedarf, Dauer und Restore-Aufwand.",
"text": "Welche Aussage zum Vollbackup stimmt?",
"answers": ["Restore ist oft einfacher als bei langen Ketten", "Es enthält nie vollständige Daten", "Es ist immer verboten"],
"correct": 0,
"explanation": "Ein vollständiger Sicherungsstand vereinfacht die Wiederherstellung."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Was bedeutet die 3-2-1-Regel grob?",
"answers": ["3 Kopien, 2 Medientypen, 1 Kopie extern", "3 Passwörter, 2 Nutzer, 1 Drucker", "3 Monitore, 2 Kabel, 1 Maus"],
"correct": 0,
"explanation": "Die Regel reduziert Risiko durch mehrere Kopien und externe Lagerung."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Warum ist eine externe oder offline Kopie sinnvoll?",
"answers": ["Sie schützt besser gegen Brand, Diebstahl oder Ransomware", "Sie macht Daten automatisch öffentlich", "Sie ersetzt alle Benutzerrechte"],
"correct": 0,
"explanation": "Getrennte Kopien erhöhen die Chance auf Wiederherstellung."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Was ist bei Cloud-Backups wichtig?",
"answers": ["Datenschutz, Verschlüsselung, Vertrag und Wiederherstellbarkeit", "Nur die Farbe des Cloud-Logos", "Keine Zugriffskontrolle"],
"correct": 0,
"explanation": "Cloud-Backups brauchen technische, rechtliche und organisatorische Bewertung."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Warum sollten Backups verschlüsselt werden?",
"answers": ["Zum Schutz vor unbefugtem Zugriff", "Damit sie langsamer gelöscht werden", "Damit sie nie wiederherstellbar sind"],
"correct": 0,
"explanation": "Verschlüsselung unterstützt die Vertraulichkeit der gesicherten Daten."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Was sollte nach einer Backup-Einrichtung dokumentiert werden?",
"answers": ["Zeitplan, Umfang, Speicherort, Verantwortliche und Restore-Verfahren", "Nur der Name des Praktikanten", "Nichts"],
"correct": 0,
"explanation": "Dokumentation macht Betrieb und Notfallwiederherstellung möglich."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Ein Backup läuft täglich, schlägt aber seit Wochen fehl. Was ist das Hauptproblem?",
"answers": ["Fehlende Überwachung oder Reaktion auf Fehler", "Zu viele erfolgreiche Tests", "Zu viel Dokumentation"],
"correct": 0,
"explanation": "Backups müssen überwacht und Fehler müssen bearbeitet werden."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Was ist bei Ransomware besonders wichtig?",
"answers": ["Nicht dauerhaft beschreibbare oder getrennte Backup-Kopien", "Backups immer im selben Ordner offen lassen", "Backups nie prüfen"],
"correct": 0,
"explanation": "Ransomware kann erreichbare Backups verschlüsseln oder löschen."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Was ist ein typischer Fehler in Backup-Konzepten?",
"answers": ["Sicherung nie wiederherstellen testen", "RPO und RTO definieren", "Zugriffe einschränken"],
"correct": 0,
"explanation": "Ungetestete Sicherungen können im Ernstfall wertlos sein."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Welche Frage ist bei Backup-Planung zentral?",
"answers": ["Wie viel Datenverlust und Ausfallzeit sind akzeptabel?", "Welche Tapete hat der Serverraum?", "Welcher Monitor ist am hellsten?"],
"correct": 0,
"explanation": "RPO und RTO bestimmen die passende Backup-Strategie."
},
{
"category": "Backup-Strategie & Praxis",
"hint": "Bewerte Sicherungsorte, Sicherheit, Tests und typische AP1-Szenarien.",
"text": "Welche Aussage ist richtig?",
"answers": ["Backup, Restore-Test und Dokumentation gehören zusammen", "Backup ohne Restore ist immer ausreichend", "Dokumentation verhindert Wiederherstellung"],
"correct": 0,
"explanation": "Ein gutes Konzept umfasst Sicherung, Prüfung und nachvollziehbare Abläufe."
}
]
}
@@ -0,0 +1,405 @@
{
"title": "Datenschutz & Datensicherheit",
"questions": [
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Welche Angabe ist eindeutig personenbezogen?",
"answers": ["Seriennummer eines Switches", "Name und E-Mail-Adresse eines Kunden", "Temperatur im Serverraum"],
"correct": 1,
"explanation": "Name und E-Mail-Adresse können direkt einer Person zugeordnet werden."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Welche Daten können indirekt personenbezogen sein?",
"answers": ["Eine IP-Adresse in Logdateien", "Eine zufällige Gehäusefarbe", "Eine leere Tabelle ohne Bezug"],
"correct": 0,
"explanation": "IP-Adressen können unter Umständen einer Person oder einem Anschluss zugeordnet werden."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Welche Aussage zu Personalnummern ist richtig?",
"answers": ["Sie sind nie personenbezogen", "Sie können Beschäftigte eindeutig identifizieren", "Sie sind nur bei Auszubildenden geschützt"],
"correct": 1,
"explanation": "Personalnummern beziehen sich auf konkrete Beschäftigte und sind personenbezogen."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Was bedeutet Anonymisierung?",
"answers": ["Personenbezug wird so entfernt, dass keine Zuordnung mehr möglich ist", "Daten werden nur umbenannt", "Daten werden unverschlüsselt gespeichert"],
"correct": 0,
"explanation": "Anonyme Daten lassen sich nicht mehr auf eine Person zurückführen."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Was bedeutet Pseudonymisierung?",
"answers": ["Identifizierende Merkmale werden ersetzt, eine Zuordnung bleibt mit Zusatzwissen möglich", "Alle Daten werden gelöscht", "Daten werden öffentlich gemacht"],
"correct": 0,
"explanation": "Pseudonyme reduzieren Risiken, beseitigen den Personenbezug aber nicht vollständig."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Welche Information ist besonders sensibel?",
"answers": ["Gesundheitsdaten eines Mitarbeiters", "Rack-Nummer eines Servers", "Hersteller eines Monitors"],
"correct": 0,
"explanation": "Gesundheitsdaten gehören zu besonders schützenswerten personenbezogenen Daten."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Was ist bei Logdateien mit Benutzerkennungen wichtig?",
"answers": ["Sie können personenbezogene Daten enthalten", "Sie sind automatisch anonym", "Sie dürfen nie ausgewertet werden"],
"correct": 0,
"explanation": "Benutzerkennungen, Zeitpunkte und Aktionen können Nutzerverhalten nachvollziehbar machen."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Welche Kombination ist personenbezogen?",
"answers": ["Abteilung, Name und Telefonnummer", "Nur die Anzahl der Switchports", "Ein leerer USB-Stick"],
"correct": 0,
"explanation": "Die Kombination ermöglicht eine klare Zuordnung zu einer Person."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Warum ist der Personenbezug in Prüfungsaufgaben wichtig?",
"answers": ["Er entscheidet, ob Datenschutzregeln zu beachten sind", "Er entscheidet nur über die Bildschirmauflösung", "Er ist nie relevant"],
"correct": 0,
"explanation": "Sobald personenbezogene Daten verarbeitet werden, greifen Datenschutzanforderungen."
},
{
"category": "Personenbezogene Daten",
"hint": "Erkenne, wann Daten sich auf eine identifizierte oder identifizierbare Person beziehen.",
"text": "Welche Aussage ist korrekt?",
"answers": ["Auch Kundendaten und Mitarbeiterdaten können personenbezogen sein", "Nur Passwörter sind personenbezogen", "Personenbezogene Daten gibt es nur in Papierakten"],
"correct": 0,
"explanation": "Personenbezogene Daten können digital oder analog und in vielen Kontexten vorkommen."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Was bedeutet Datenminimierung?",
"answers": ["Nur Daten verarbeiten, die für den Zweck notwendig sind", "Alle verfügbaren Daten speichern", "Daten nie löschen"],
"correct": 0,
"explanation": "Es sollen nicht mehr personenbezogene Daten verarbeitet werden als nötig."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Was bedeutet Zweckbindung?",
"answers": ["Daten dürfen nur für festgelegte Zwecke verarbeitet werden", "Daten dürfen für alles genutzt werden", "Der Zweck muss geheim bleiben"],
"correct": 0,
"explanation": "Der Zweck muss vorab feststehen und die Verarbeitung daran gebunden sein."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Was beschreibt der Grundsatz der Richtigkeit?",
"answers": ["Personenbezogene Daten sollen sachlich richtig und aktuell sein", "Daten sollen möglichst bunt sein", "Daten sollen nie geprüft werden"],
"correct": 0,
"explanation": "Unrichtige Daten können zu falschen Entscheidungen führen."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Was bedeutet Speicherbegrenzung?",
"answers": ["Daten nur so lange speichern, wie es für den Zweck nötig ist", "Daten unbegrenzt behalten", "Nur kleine Dateien speichern"],
"correct": 0,
"explanation": "Personenbezogene Daten brauchen Löschfristen oder Prüffristen."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Was bedeutet Integrität und Vertraulichkeit im Datenschutzkontext?",
"answers": ["Daten vor unbefugtem Zugriff, Verlust und Manipulation schützen", "Daten öffentlich verteilen", "Daten ohne Backup speichern"],
"correct": 0,
"explanation": "Dieser Grundsatz verlangt angemessene Sicherheit der Verarbeitung."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Was ist Rechenschaftspflicht?",
"answers": ["Nachweisen können, dass Datenschutzregeln eingehalten werden", "Nur mündlich behaupten, alles sei sicher", "Alle Nachweise löschen"],
"correct": 0,
"explanation": "Organisationen müssen Datenschutzmaßnahmen dokumentieren und belegen können."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Welche Verarbeitung ist problematisch?",
"answers": ["Kundendaten ohne Zweck unbegrenzt speichern", "Zugriffe rollenbasiert einschränken", "Daten nach Frist löschen"],
"correct": 0,
"explanation": "Ohne Zweck und Frist werden Zweckbindung und Speicherbegrenzung verletzt."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Warum braucht eine Verarbeitung eine Rechtsgrundlage?",
"answers": ["Damit personenbezogene Daten rechtmäßig verarbeitet werden", "Damit die Daten größer werden", "Damit Backups schneller laufen"],
"correct": 0,
"explanation": "Rechtmäßigkeit ist ein zentraler Grundsatz."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Welche Aussage passt zur Transparenz?",
"answers": ["Betroffene sollen verständlich informiert werden", "Verarbeitung soll geheim bleiben", "Informationen dürfen absichtlich verwirrend sein"],
"correct": 0,
"explanation": "Transparenz verlangt verständliche Informationen über die Verarbeitung."
},
{
"category": "DSGVO-Grundsätze",
"hint": "Grundsätze helfen, Verarbeitung rechtmäßig und nachvollziehbar zu bewerten.",
"text": "Was ist ein typischer Prüfungsfehler?",
"answers": ["Mehr Daten erfassen als für den Auftrag nötig", "Zugriffsrechte begrenzen", "Löschfristen definieren"],
"correct": 0,
"explanation": "Übermäßige Datenerhebung widerspricht Datenminimierung."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Was bedeutet Auskunftsrecht?",
"answers": ["Betroffene können Informationen über gespeicherte Daten verlangen", "Betroffene müssen alle Daten selbst sichern", "Betroffene verlieren alle Rechte"],
"correct": 0,
"explanation": "Betroffene dürfen erfahren, welche Daten zu welchem Zweck verarbeitet werden."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Was bedeutet Recht auf Berichtigung?",
"answers": ["Falsche personenbezogene Daten müssen korrigiert werden", "Daten müssen immer veröffentlicht werden", "Nur Passwörter dürfen geändert werden"],
"correct": 0,
"explanation": "Unrichtige Daten können berichtigt werden."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Was bedeutet Recht auf Löschung?",
"answers": ["Daten können unter bestimmten Voraussetzungen gelöscht werden", "Alle Daten müssen immer sofort gelöscht werden", "Daten dürfen nie gelöscht werden"],
"correct": 0,
"explanation": "Löschung hängt von Zweck, Rechtsgrundlage und Aufbewahrungspflichten ab."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Was bedeutet Widerspruchsrecht?",
"answers": ["Betroffene können bestimmten Verarbeitungen widersprechen", "Betroffene müssen jede Verarbeitung akzeptieren", "Nur Administratoren dürfen widersprechen"],
"correct": 0,
"explanation": "Unter bestimmten Bedingungen kann Verarbeitung abgelehnt werden."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Was bedeutet Datenübertragbarkeit?",
"answers": ["Daten in einem strukturierten, gängigen Format erhalten können", "Daten nur auf Papier bekommen", "Daten nie exportieren dürfen"],
"correct": 0,
"explanation": "Das Recht erleichtert Wechsel zwischen Diensten."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Wer ist eine betroffene Person?",
"answers": ["Die Person, auf die sich personenbezogene Daten beziehen", "Nur der Datenschutzbeauftragte", "Nur der Serveradministrator"],
"correct": 0,
"explanation": "Betroffen ist die identifizierte oder identifizierbare Person."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Was sollte bei einer Auskunftsanfrage zuerst geprüft werden?",
"answers": ["Identität der anfragenden Person", "Monitorauflösung", "Farbe der Datenbank"],
"correct": 0,
"explanation": "Daten dürfen nicht an unberechtigte Personen herausgegeben werden."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Warum dürfen Betroffenenrechte nicht ignoriert werden?",
"answers": ["Sie sind rechtlich relevante Ansprüche", "Sie sind freiwillige Dekoration", "Sie gelten nur im Urlaub"],
"correct": 0,
"explanation": "Organisationen müssen Anfragen angemessen bearbeiten."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Was ist bei Löschanfragen zu beachten?",
"answers": ["Ob gesetzliche Aufbewahrungspflichten entgegenstehen", "Ob der Drucker eingeschaltet ist", "Ob die Datei hübsch benannt ist"],
"correct": 0,
"explanation": "Nicht jede Löschung ist sofort möglich, wenn Pflichten zur Aufbewahrung bestehen."
},
{
"category": "Betroffenenrechte",
"hint": "Betroffene Personen haben Rechte gegenüber Verantwortlichen.",
"text": "Welche Antwort auf eine Betroffenenanfrage ist professionell?",
"answers": ["Anfrage dokumentieren, prüfen und fristgerecht beantworten", "Anfrage löschen", "Anfrage öffentlich posten"],
"correct": 0,
"explanation": "Dokumentation und fristgerechte Bearbeitung sind wichtig."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Wofür steht TOM?",
"answers": ["Technische und organisatorische Maßnahmen", "Tägliche Online-Meldung", "Temporäre Ordner-Migration"],
"correct": 0,
"explanation": "TOMs sind Schutzmaßnahmen für die Verarbeitung personenbezogener Daten."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Welches Schutzziel wird durch Verschlüsselung besonders unterstützt?",
"answers": ["Vertraulichkeit", "Lautstärke", "Bildschirmgröße"],
"correct": 0,
"explanation": "Verschlüsselung schützt Inhalte vor unberechtigtem Lesen."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Welches Schutzziel wird durch Backups besonders unterstützt?",
"answers": ["Verfügbarkeit", "Farbtreue", "Kabellänge"],
"correct": 0,
"explanation": "Backups helfen, Daten nach Verlust wiederherzustellen."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Was bedeutet Integrität?",
"answers": ["Daten sind vollständig und unverändert", "Daten sind immer öffentlich", "Daten sind besonders groß"],
"correct": 0,
"explanation": "Integrität schützt vor unbemerkter Manipulation oder Fehlern."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Welche Maßnahme unterstützt Zugriffskontrolle?",
"answers": ["Rollen- und Rechtekonzept", "Offene Admin-Passwörter", "Gemeinsamer Account für alle"],
"correct": 0,
"explanation": "Rollen und Rechte begrenzen Zugriff nach Aufgabe."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Warum ist Protokollierung wichtig?",
"answers": ["Zugriffe und Änderungen können nachvollzogen werden", "Alle Daten werden automatisch anonym", "Sie ersetzt jedes Backup"],
"correct": 0,
"explanation": "Logs unterstützen Kontrolle, Nachvollziehbarkeit und Fehleranalyse."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Was ist ein gutes Passwortkonzept?",
"answers": ["Starke Passwörter, individuelle Accounts und wenn möglich Mehrfaktor-Authentifizierung", "Ein Passwort für alle", "Passwörter auf Monitor kleben"],
"correct": 0,
"explanation": "Individuelle starke Authentifizierung reduziert Missbrauch."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Welche organisatorische Maßnahme ist sinnvoll?",
"answers": ["Mitarbeiter zu Datenschutz und Sicherheit schulen", "Sicherheitsregeln geheim halten", "Keine Zuständigkeiten definieren"],
"correct": 0,
"explanation": "Schulung hilft, Fehlverhalten und Unsicherheit zu reduzieren."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Was bedeutet Need-to-know?",
"answers": ["Zugriff nur, wenn er für die Aufgabe nötig ist", "Alle dürfen alles sehen", "Nur externe Personen bekommen Zugriff"],
"correct": 0,
"explanation": "Need-to-know begrenzt Zugriff auf notwendige Informationen."
},
{
"category": "TOMs & Schutzziele",
"hint": "Technische und organisatorische Maßnahmen schützen Daten im Betrieb.",
"text": "Welche Maßnahme passt zur Verfügbarkeit?",
"answers": ["USV, Backup und Redundanz", "Unverschlüsselte Passwortliste", "Keine Wartung"],
"correct": 0,
"explanation": "Verfügbarkeit wird durch Ausfallschutz und Wiederherstellbarkeit unterstützt."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Ein USB-Stick mit Kundendaten wurde verloren. Was ist sinnvoll?",
"answers": ["Vorfall melden, Risiko prüfen und zuständige Stellen informieren", "Den Vorfall verschweigen", "Neue Aufkleber drucken"],
"correct": 0,
"explanation": "Datenschutzvorfälle müssen bewertet und nach Prozess behandelt werden."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Wer ist Verantwortlicher im Datenschutz?",
"answers": ["Die Stelle, die über Zweck und Mittel der Verarbeitung entscheidet", "Immer der Auszubildende", "Immer der Druckerhersteller"],
"correct": 0,
"explanation": "Verantwortliche bestimmen Zweck und Mittel der Verarbeitung."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Was ist Auftragsverarbeitung?",
"answers": ["Ein Dienstleister verarbeitet personenbezogene Daten im Auftrag", "Ein Kunde kauft einen Monitor", "Ein Projekt wird ohne Auftrag begonnen"],
"correct": 0,
"explanation": "Bei Auftragsverarbeitung braucht es klare vertragliche Regelungen."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Ein externer IT-Dienstleister wartet ein System mit Kundendaten. Was ist zu prüfen?",
"answers": ["Zugriff, Vertrag, Vertraulichkeit und Zweckbindung", "Nur die Farbe seines Firmenwagens", "Ob er private Musik hört"],
"correct": 0,
"explanation": "Externe Zugriffe müssen rechtlich und technisch geregelt sein."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Was ist bei Bildschirmarbeitsplätzen mit Kundendaten sinnvoll?",
"answers": ["Bildschirm sperren und Sichtschutz bei Bedarf nutzen", "Daten dauerhaft offen anzeigen", "Passwort unter die Tastatur legen"],
"correct": 0,
"explanation": "Arbeitsplätze müssen gegen unbefugte Einsicht geschützt werden."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Warum sollten alte Datenträger sicher gelöscht oder vernichtet werden?",
"answers": ["Damit personenbezogene Daten nicht wiederhergestellt werden können", "Damit sie schöner aussehen", "Damit Backups schneller werden"],
"correct": 0,
"explanation": "Normales Löschen reicht oft nicht gegen Wiederherstellung."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Was ist bei Testdaten in Entwicklungssystemen sinnvoll?",
"answers": ["Keine echten personenbezogenen Daten nutzen oder sie anonymisieren", "Produktivdaten frei kopieren", "Kundendaten öffentlich bereitstellen"],
"correct": 0,
"explanation": "Testsysteme sollten keine unnötigen echten personenbezogenen Daten enthalten."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Was sollte bei neuen IT-Systemen früh bedacht werden?",
"answers": ["Datenschutz durch Technikgestaltung und datenschutzfreundliche Voreinstellungen", "Nur die Gehäusefarbe", "Möglichst viele unnötige Daten sammeln"],
"correct": 0,
"explanation": "Privacy by Design und Privacy by Default sind wichtige Prinzipien."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Ein Kollege bittet um fremde Personaldaten ohne dienstlichen Grund. Was ist richtig?",
"answers": ["Zugriff verweigern und auf Berechtigung verweisen", "Daten sofort senden", "Daten öffentlich im Chat posten"],
"correct": 0,
"explanation": "Ohne berechtigten Zweck darf kein Zugriff erfolgen."
},
{
"category": "Praxisfälle & Verantwortung",
"hint": "Wende Datenschutz in typischen AP1-Handlungssituationen an.",
"text": "Warum ist Datenschutz in AP1-Aufgaben oft mit IT-Sicherheit verbunden?",
"answers": ["Weil technische Schutzmaßnahmen personenbezogene Daten sichern", "Weil Datenschutz nur aus Firewalls besteht", "Weil Sicherheit Datenschutz ersetzt"],
"correct": 0,
"explanation": "Datenschutz und Datensicherheit überschneiden sich, sind aber nicht identisch."
}
]
}
@@ -0,0 +1,405 @@
{
"title": "OSI-Modell",
"questions": [
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Wozu dient das OSI-Modell hauptsächlich?",
"answers": ["Zur strukturierten Beschreibung von Netzwerkkommunikation", "Zum Formatieren von Festplatten", "Zum Berechnen von Rabatten"],
"correct": 0,
"explanation": "Das OSI-Modell teilt Netzwerkkommunikation in sieben verständliche Schichten."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Wie viele Schichten hat das OSI-Modell?",
"answers": ["4", "7", "12"],
"correct": 1,
"explanation": "Das OSI-Modell besteht aus sieben Schichten."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Welche Schicht ist die unterste Schicht?",
"answers": ["Anwendung", "Bitübertragung", "Transport"],
"correct": 1,
"explanation": "Schicht 1 ist die Bitübertragungsschicht."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Welche Schicht ist die oberste Schicht?",
"answers": ["Anwendung", "Vermittlung", "Sicherung"],
"correct": 0,
"explanation": "Schicht 7 ist die Anwendungsschicht."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Warum ist das OSI-Modell in der Fehleranalyse nützlich?",
"answers": ["Fehler können schichtweise eingegrenzt werden", "Es löscht automatisch Störungen", "Es ersetzt jede Dokumentation"],
"correct": 0,
"explanation": "Man prüft vom physischen Anschluss bis zur Anwendung systematisch."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Welche Reihenfolge ist korrekt?",
"answers": ["Bitübertragung, Sicherung, Vermittlung, Transport", "Anwendung, Sicherung, Bitübertragung, Transport", "Transport, Darstellung, Bitübertragung, Sicherung"],
"correct": 0,
"explanation": "Die unteren vier Schichten lauten 1 Bitübertragung, 2 Sicherung, 3 Vermittlung, 4 Transport."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Was bedeutet Kapselung in Netzwerkmodellen?",
"answers": ["Jede Schicht fügt eigene Informationen hinzu", "Daten werden immer gelöscht", "Nur Kabel werden beschriftet"],
"correct": 0,
"explanation": "Beim Senden werden Daten von Schicht zu Schicht mit Headern versehen."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Welche Aussage ist korrekt?",
"answers": ["Protokolle lassen sich bestimmten Schichten zuordnen", "Alle Protokolle gehören immer zu Schicht 1", "Das OSI-Modell gilt nur für Drucker"],
"correct": 0,
"explanation": "Beispiele sind Ethernet auf Schicht 2, IP auf Schicht 3 und HTTP auf Schicht 7."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Welcher Begriff passt zum OSI-Modell?",
"answers": ["Schichtenmodell", "Bilanzkonto", "Zeiterfassung"],
"correct": 0,
"explanation": "OSI ist ein Schichtenmodell für Kommunikation."
},
{
"category": "OSI-Grundlagen",
"hint": "Verstehe Zweck, Reihenfolge und Nutzen des Schichtenmodells.",
"text": "Was ist in AP1 besonders wichtig?",
"answers": ["Typische Geräte, Protokolle und Fehler den Schichten zuordnen", "Alle RFCs auswendig lernen", "Nur IPv6-Adressen malen"],
"correct": 0,
"explanation": "Prüfungsaufgaben arbeiten oft mit Zuordnung und Fehlerdiagnose."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Was gehört typischerweise zu Schicht 1?",
"answers": ["Kabel und elektrische Signale", "HTTP-Statuscodes", "Benutzerrechte"],
"correct": 0,
"explanation": "Schicht 1 beschreibt die physische Übertragung."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Welches Gerät arbeitet klassisch auf Schicht 2?",
"answers": ["Switch", "Webserver", "Druckertreiber"],
"correct": 0,
"explanation": "Switches treffen Weiterleitungsentscheidungen anhand von MAC-Adressen."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Welche Adresse gehört zu Schicht 2?",
"answers": ["MAC-Adresse", "IP-Adresse", "URL"],
"correct": 0,
"explanation": "MAC-Adressen werden auf der Sicherungsschicht verwendet."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Welche Einheit passt zu Schicht 2?",
"answers": ["Frame", "Segment", "Datei"],
"correct": 0,
"explanation": "Auf Schicht 2 werden Daten typischerweise als Frames betrachtet."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Ein Netzwerkkabel ist defekt. Welche Schicht ist zuerst betroffen?",
"answers": ["Schicht 1", "Schicht 4", "Schicht 7"],
"correct": 0,
"explanation": "Kabel gehören zur Bitübertragungsschicht."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Was macht ein Switch mit seiner MAC-Tabelle?",
"answers": ["Er ordnet MAC-Adressen Ports zu", "Er vergibt HTTP-Cookies", "Er berechnet Kreditzinsen"],
"correct": 0,
"explanation": "Die MAC-Tabelle hilft beim gezielten Weiterleiten von Frames."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Was ist ein typisches Schicht-1-Problem?",
"answers": ["Kein Link-Signal am Port", "Falsches Passwort im Webformular", "Falscher Mehrwertsteuersatz"],
"correct": 0,
"explanation": "Fehlendes Link-Signal deutet auf physische Verbindung oder Portproblem hin."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Was ist ein typisches Schicht-2-Thema?",
"answers": ["VLAN", "DNS-Name", "HTML-Formular"],
"correct": 0,
"explanation": "VLANs werden häufig der Sicherungsschicht zugeordnet."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Was prüfst du bei Verdacht auf Schicht-1-Fehler?",
"answers": ["Kabel, Link-LED, Port und physische Verbindung", "Nur den Browsercache", "Nur Benutzerrechte"],
"correct": 0,
"explanation": "Schicht 1 beginnt bei der physischen Verbindung."
},
{
"category": "Schicht 1-2: Bitübertragung & Sicherung",
"hint": "Kabel, Signale, MAC-Adressen, Frames und Switches sicher zuordnen.",
"text": "Welche Aussage zu Switches ist korrekt?",
"answers": ["Sie arbeiten überwiegend mit MAC-Adressen", "Sie ersetzen jede IP-Adresse", "Sie sind immer Webbrowser"],
"correct": 0,
"explanation": "Switches leiten Frames anhand von MAC-Adressen weiter."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Auf welcher Schicht arbeitet IP?",
"answers": ["Schicht 3", "Schicht 1", "Schicht 7"],
"correct": 0,
"explanation": "IP gehört zur Vermittlungsschicht."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Auf welcher Schicht arbeitet TCP?",
"answers": ["Schicht 4", "Schicht 2", "Schicht 6"],
"correct": 0,
"explanation": "TCP ist ein Transportprotokoll."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Welches Gerät arbeitet klassisch auf Schicht 3?",
"answers": ["Router", "Hub", "Monitor"],
"correct": 0,
"explanation": "Router verbinden Netze anhand von IP-Informationen."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Welche Adresse gehört zu Schicht 3?",
"answers": ["IP-Adresse", "MAC-Adresse", "Seriennummer"],
"correct": 0,
"explanation": "IP-Adressen dienen zur logischen Adressierung im Netzwerk."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Welche Protokolle gehören typischerweise zu Schicht 4?",
"answers": ["TCP und UDP", "HTTP und HTML", "VGA und HDMI"],
"correct": 0,
"explanation": "TCP und UDP sind Transportprotokolle."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Wozu dienen Ports?",
"answers": ["Zur Zuordnung von Daten zu Anwendungen oder Diensten", "Zur Stromversorgung", "Zur Berechnung von Subventionen"],
"correct": 0,
"explanation": "Ports helfen, Daten an den richtigen Dienst weiterzugeben."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Was ist ein typischer TCP-Vorteil?",
"answers": ["Zuverlässige, verbindungsorientierte Übertragung", "Keine Fehlerkontrolle", "Nur Broadcast"],
"correct": 0,
"explanation": "TCP bestätigt Daten und sorgt für Reihenfolge und Wiederholung bei Verlust."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Was ist ein typischer UDP-Vorteil?",
"answers": ["Geringer Overhead und schnelle Übertragung", "Garantierte Zustellung jedes Pakets", "Automatische Verschlüsselung"],
"correct": 0,
"explanation": "UDP ist schlanker, aber bietet weniger Zuverlässigkeitsmechanismen."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Ein Host hat eine falsche Standardgateway-Adresse. Welche Schicht ist besonders betroffen?",
"answers": ["Schicht 3", "Schicht 1", "Schicht 6"],
"correct": 0,
"explanation": "Gateway und Routing gehören zur Vermittlungsschicht."
},
{
"category": "Schicht 3-4: Vermittlung & Transport",
"hint": "IP, Routing, TCP, UDP und Ports sauber unterscheiden.",
"text": "Ein Dienst hört nicht auf Port 443. Welche Schicht ist bei der Portprüfung relevant?",
"answers": ["Schicht 4", "Schicht 1", "Schicht 2"],
"correct": 0,
"explanation": "Ports sind ein Thema der Transportschicht."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Welche Schicht ist die Anwendungsschicht?",
"answers": ["Schicht 7", "Schicht 3", "Schicht 1"],
"correct": 0,
"explanation": "Schicht 7 stellt Dienste für Anwendungen bereit."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Welches Protokoll gehört typischerweise zur Anwendungsschicht?",
"answers": ["HTTP", "IP", "Ethernet"],
"correct": 0,
"explanation": "HTTP ist ein Anwendungsprotokoll."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Welche Aufgabe passt zur Darstellungsschicht?",
"answers": ["Datenformat, Kodierung oder Verschlüsselung", "Kabel einstecken", "MAC-Tabelle lernen"],
"correct": 0,
"explanation": "Schicht 6 befasst sich unter anderem mit Darstellung und Kodierung."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Welche Aufgabe passt zur Sitzungsschicht?",
"answers": ["Sitzungen und Dialoge zwischen Systemen steuern", "IP-Routing durchführen", "Kabelschirmung prüfen"],
"correct": 0,
"explanation": "Schicht 5 koordiniert Sitzungen und Verbindungsdialoge."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "DNS wird in Prüfungen meist welcher Schicht zugeordnet?",
"answers": ["Schicht 7", "Schicht 2", "Schicht 1"],
"correct": 0,
"explanation": "DNS ist ein Anwendungsdienst zur Namensauflösung."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "SMTP wird typischerweise wofür verwendet?",
"answers": ["E-Mail-Versand", "MAC-Adressierung", "Stromversorgung"],
"correct": 0,
"explanation": "SMTP ist ein Protokoll für den Versand von E-Mails."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Welche Aussage zu HTTPS ist passend?",
"answers": ["Es schützt HTTP-Kommunikation durch TLS", "Es ersetzt jedes Routing", "Es gehört nur zu Schicht 1"],
"correct": 0,
"explanation": "HTTPS nutzt TLS für verschlüsselte Webkommunikation."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Ein Browser zeigt 'DNS_PROBE_FINISHED'. Welcher Bereich ist naheliegend?",
"answers": ["Namensauflösung auf Anwendungsebene", "Defektes Netzwerkkabel zwingend", "Falsche Mehrwertsteuer"],
"correct": 0,
"explanation": "DNS-Probleme liegen bei der Namensauflösung, typischerweise Anwendungsschicht."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Welches Beispiel passt zur Darstellungsschicht?",
"answers": ["Zeichencodierung wie UTF-8", "Switchport lernen", "Subnetzmaske berechnen"],
"correct": 0,
"explanation": "Zeichencodierung betrifft die Darstellung von Daten."
},
{
"category": "Schicht 5-7: Sitzung, Darstellung, Anwendung",
"hint": "Dienste, Formate, Verschlüsselung und Anwendungsprotokolle zuordnen.",
"text": "Welche Protokolle sind typische Anwendungsprotokolle?",
"answers": ["HTTP, DNS, SMTP", "IP, ICMP, ARP", "Kupfer, Glasfaser, Funk"],
"correct": 0,
"explanation": "HTTP, DNS und SMTP werden meist der Anwendungsschicht zugeordnet."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Ein PC hat keine Link-LED am Netzwerkport. Was prüfst du zuerst?",
"answers": ["Kabel, Port und physische Verbindung", "DNS-Eintrag", "HTTP-Cookie"],
"correct": 0,
"explanation": "Ohne Link ist zuerst Schicht 1 zu prüfen."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Ein PC hat Link, aber keine gültige IP-Adresse. Welche Ebene ist naheliegend?",
"answers": ["Schicht 3 beziehungsweise IP-Konfiguration", "Nur Schicht 7", "Nur das Netzteil"],
"correct": 0,
"explanation": "IP-Adresse, Gateway und Netzmaske gehören zur Vermittlungsschicht."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Ping zur IP funktioniert, aber der Name nicht. Was ist wahrscheinlich?",
"answers": ["DNS-Problem", "Kabel zwingend defekt", "Monitor kaputt"],
"correct": 0,
"explanation": "Wenn IP erreichbar ist, aber Name nicht, liegt der Fokus auf Namensauflösung."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Ein Webserver ist per Ping erreichbar, aber HTTPS geht nicht. Was prüfst du?",
"answers": ["Port 443, Dienst und Firewall", "Nur die Kabelfarbe", "Nur den Druckertreiber"],
"correct": 0,
"explanation": "Hier sind Transport- und Anwendungsebene relevant."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Warum ist schichtweises Vorgehen sinnvoll?",
"answers": ["Es verhindert planloses Raten", "Es macht Dokumentation unnötig", "Es löscht automatisch Fehler"],
"correct": 0,
"explanation": "Schichtweises Prüfen grenzt Ursachen systematisch ein."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Welche Reihenfolge ist bei Fehlersuche oft sinnvoll?",
"answers": ["Physisch, lokale Konfiguration, Routing, Ports, Anwendung", "Anwendung, Rechnung, Gehäusefarbe", "Nur Neustart ohne Prüfung"],
"correct": 0,
"explanation": "Man beginnt häufig unten und arbeitet sich nach oben."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Ein falsches VLAN am Switchport betrifft vor allem welche Schicht?",
"answers": ["Schicht 2", "Schicht 6", "Schicht 7"],
"correct": 0,
"explanation": "VLAN-Zuordnung ist ein Thema der Sicherungsschicht."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Ein falsches Standardgateway verhindert Zugriff auf andere Netze. Welche Schicht ist betroffen?",
"answers": ["Schicht 3", "Schicht 1", "Schicht 5"],
"correct": 0,
"explanation": "Gateway und Routing gehören zu Schicht 3."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Ein Dienst läuft, aber die Firewall blockiert den Port. Welche Prüfung ist relevant?",
"answers": ["Transportebene und Portfreigabe", "Nur Bildschirmhelligkeit", "Nur Speicherplatz"],
"correct": 0,
"explanation": "Ports und Verbindungen gehören zur Transportschicht."
},
{
"category": "Fehleranalyse nach OSI",
"hint": "Gehe systematisch von physischer Verbindung bis Anwendung vor.",
"text": "Eine Webseite liefert HTTP 500. Wo liegt der Fokus eher?",
"answers": ["Anwendung oder Serverdienst", "Defektes Patchkabel zwingend", "MAC-Adresse des Monitors"],
"correct": 0,
"explanation": "HTTP-Fehlercodes gehören zur Anwendungsebene beziehungsweise zum Webdienst."
}
]
}
File diff suppressed because it is too large Load Diff
@@ -0,0 +1,245 @@
{
"title": "Datenbanksysteme",
"questions": [
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Was beschreibt Tabelle am besten?",
"answers": [
"Sie strukturiert Daten in Zeilen und Spalten.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Sie strukturiert Daten in Zeilen und Spalten."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Welche Aussage zu Datensatz ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Eine Zeile beschreibt ein Objekt oder Ereignis.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Eine Zeile beschreibt ein Objekt oder Ereignis."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Woran erkennst du Attribut in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Eine Spalte beschreibt eine Eigenschaft."
],
"correct": 2,
"explanation": "Eine Spalte beschreibt eine Eigenschaft."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Was ist bei Primärschlüssel besonders wichtig?",
"answers": [
"Er identifiziert Datensätze eindeutig.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Er identifiziert Datensätze eindeutig."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Was beschreibt Fremdschlüssel am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Er verweist auf Datensätze anderer Tabellen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Er verweist auf Datensätze anderer Tabellen."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Welche Aussage zu Relation ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Beziehung zwischen Tabellen."
],
"correct": 2,
"explanation": "Beziehung zwischen Tabellen."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Woran erkennst du Redundanz in einer AP1-Aufgabe?",
"answers": [
"Doppelte Daten können Inkonsistenzen erzeugen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Doppelte Daten können Inkonsistenzen erzeugen."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Was ist bei Normalisierung besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Sie reduziert unnötige Wiederholungen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Sie reduziert unnötige Wiederholungen."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Was beschreibt DBMS am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Es verwaltet Daten, Zugriffe und Transaktionen."
],
"correct": 2,
"explanation": "Es verwaltet Daten, Zugriffe und Transaktionen."
},
{
"category": "Datenbank-Grundlagen",
"hint": "Tabellen, Datensätze und Beziehungen verstehen.",
"text": "Welche Aussage zu Transaktion ist richtig?",
"answers": [
"Sie fasst Operationen zuverlässig zusammen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Sie fasst Operationen zuverlässig zusammen."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Was beschreibt SELECT am besten?",
"answers": [
"Liest Daten aus Tabellen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Liest Daten aus Tabellen."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Welche Aussage zu INSERT ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Fügt neue Datensätze ein.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Fügt neue Datensätze ein."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Woran erkennst du UPDATE in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Ändert bestehende Datensätze."
],
"correct": 2,
"explanation": "Ändert bestehende Datensätze."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Was ist bei DELETE besonders wichtig?",
"answers": [
"Löscht Datensätze.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Löscht Datensätze."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Was beschreibt WHERE am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Filtert Datensätze nach Bedingungen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Filtert Datensätze nach Bedingungen."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Welche Aussage zu JOIN ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Verknüpft Tabellen über Beziehungen."
],
"correct": 2,
"explanation": "Verknüpft Tabellen über Beziehungen."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Woran erkennst du Backup in einer AP1-Aufgabe?",
"answers": [
"Datenbanken brauchen Sicherung und Restore-Test.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Datenbanken brauchen Sicherung und Restore-Test."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Was ist bei Rechtekonzept besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Nutzer sollten nur notwendige Rechte haben.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Nutzer sollten nur notwendige Rechte haben."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Was beschreibt Datenschutz am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Personenbezogene Daten müssen geschützt werden."
],
"correct": 2,
"explanation": "Personenbezogene Daten müssen geschützt werden."
},
{
"category": "SQL & Betrieb",
"hint": "Abfragen, Rechte und Betriebsaspekte einordnen.",
"text": "Welche Aussage zu Index ist richtig?",
"answers": [
"Kann Abfragen beschleunigen, braucht aber Speicher.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Kann Abfragen beschleunigen, braucht aber Speicher."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "DSL und Internetanschluss",
"questions": [
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Was beschreibt Downloadrate am besten?",
"answers": [
"Datenrate aus dem Internet zum Kunden.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Datenrate aus dem Internet zum Kunden."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Welche Aussage zu Uploadrate ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Datenrate vom Kunden ins Internet.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Datenrate vom Kunden ins Internet."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Woran erkennst du Latenz in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Zeitverzögerung einer Verbindung."
],
"correct": 2,
"explanation": "Zeitverzögerung einer Verbindung."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Was ist bei Bandbreite besonders wichtig?",
"answers": [
"Maximale Datenübertragungsrate.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Maximale Datenübertragungsrate."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Was beschreibt Router am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Verbindet lokales Netz mit dem Internet.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Verbindet lokales Netz mit dem Internet."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Welche Aussage zu Modem ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Setzt Anschlusssignal für Datenkommunikation um."
],
"correct": 2,
"explanation": "Setzt Anschlusssignal für Datenkommunikation um."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Woran erkennst du Provider in einer AP1-Aufgabe?",
"answers": [
"Stellt den Internetanschluss bereit.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Stellt den Internetanschluss bereit."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Was ist bei Verfügbarkeit besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Beschreibt, wie zuverlässig ein Anschluss nutzbar ist.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Beschreibt, wie zuverlässig ein Anschluss nutzbar ist."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Was beschreibt Fallback am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Ersatzverbindung etwa über Mobilfunk."
],
"correct": 2,
"explanation": "Ersatzverbindung etwa über Mobilfunk."
},
{
"category": "Anschluss & Bandbreite",
"hint": "Technische Anschlusswerte richtig deuten.",
"text": "Welche Aussage zu SLA ist richtig?",
"answers": [
"Vereinbarung über Servicequalität und Reaktionszeiten.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Vereinbarung über Servicequalität und Reaktionszeiten."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Was beschreibt Cloud-Backup am besten?",
"answers": [
"Benötigt ausreichend Uploadrate.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Benötigt ausreichend Uploadrate."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Welche Aussage zu Videokonferenz ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Benötigt Bandbreite und niedrige Latenz.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Benötigt Bandbreite und niedrige Latenz."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Woran erkennst du DNS-Problem in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"IP funktioniert, Name aber nicht."
],
"correct": 2,
"explanation": "IP funktioniert, Name aber nicht."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Was ist bei Router-Neustart besonders wichtig?",
"answers": [
"Kann einfache Verbindungsprobleme beheben, ersetzt aber keine Analyse.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Kann einfache Verbindungsprobleme beheben, ersetzt aber keine Analyse."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Was beschreibt Leitungsstörung am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Kann Paketverlust oder Abbrüche verursachen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Kann Paketverlust oder Abbrüche verursachen."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Welche Aussage zu WLAN vs DSL ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"WLAN-Probleme sind nicht automatisch Anschlussprobleme."
],
"correct": 2,
"explanation": "WLAN-Probleme sind nicht automatisch Anschlussprobleme."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Woran erkennst du Messung in einer AP1-Aufgabe?",
"answers": [
"Speedtests müssen richtig interpretiert werden.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Speedtests müssen richtig interpretiert werden."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Was ist bei NAT besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Übersetzt private interne Adressen nach außen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Übersetzt private interne Adressen nach außen."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Was beschreibt Firewall am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Kann Dienste blockieren."
],
"correct": 2,
"explanation": "Kann Dienste blockieren."
},
{
"category": "Praxis & Fehleranalyse",
"hint": "Typische Anschlussprobleme bewerten.",
"text": "Welche Aussage zu Dokumentation ist richtig?",
"answers": [
"Zugangsdaten und Vertragsdaten müssen sicher dokumentiert sein.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Zugangsdaten und Vertragsdaten müssen sicher dokumentiert sein."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "Storage Systeme",
"questions": [
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Was beschreibt DAS am besten?",
"answers": [
"Direkt angeschlossener Speicher am Host.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Direkt angeschlossener Speicher am Host."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Welche Aussage zu NAS ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Dateibasierter Speicher über das Netzwerk.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Dateibasierter Speicher über das Netzwerk."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Woran erkennst du SAN in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Blockbasierter Speicher über ein Speichernetz."
],
"correct": 2,
"explanation": "Blockbasierter Speicher über ein Speichernetz."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Was ist bei iSCSI besonders wichtig?",
"answers": [
"Blockzugriff über IP-Netzwerke.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Blockzugriff über IP-Netzwerke."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Was beschreibt Fibre Channel am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Technologie für performante SAN-Umgebungen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Technologie für performante SAN-Umgebungen."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Welche Aussage zu SMB ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Typisches Protokoll für Dateifreigaben."
],
"correct": 2,
"explanation": "Typisches Protokoll für Dateifreigaben."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Woran erkennst du NFS in einer AP1-Aufgabe?",
"answers": [
"Dateifreigaben häufig in Unix/Linux-Umgebungen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Dateifreigaben häufig in Unix/Linux-Umgebungen."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Was ist bei Blockspeicher besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Wirkt für den Host wie ein Laufwerk.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Wirkt für den Host wie ein Laufwerk."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Was beschreibt Dateispeicher am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Stellt Dateien und Ordner über Freigaben bereit."
],
"correct": 2,
"explanation": "Stellt Dateien und Ordner über Freigaben bereit."
},
{
"category": "DAS, NAS, SAN",
"hint": "Speicherkonzepte sicher unterscheiden.",
"text": "Welche Aussage zu Storage-Auswahl ist richtig?",
"answers": [
"Anforderungen an Performance, Kosten und Verwaltung entscheiden.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Anforderungen an Performance, Kosten und Verwaltung entscheiden."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Was beschreibt RAID am besten?",
"answers": [
"Kann Verfügbarkeit verbessern, ersetzt aber kein Backup.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Kann Verfügbarkeit verbessern, ersetzt aber kein Backup."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Welche Aussage zu Snapshots ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Erlauben schnelle Zustände, ersetzen aber nicht immer Backups.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Erlauben schnelle Zustände, ersetzen aber nicht immer Backups."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Woran erkennst du Kapazitätsplanung in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Wachstum und Reserven müssen eingeplant werden."
],
"correct": 2,
"explanation": "Wachstum und Reserven müssen eingeplant werden."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Was ist bei Zugriffsrechte besonders wichtig?",
"answers": [
"Freigaben brauchen passende Berechtigungen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Freigaben brauchen passende Berechtigungen."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Was beschreibt Performance am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"IOPS, Latenz und Durchsatz können wichtig sein.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "IOPS, Latenz und Durchsatz können wichtig sein."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Welche Aussage zu Redundanz ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Mehrfach ausgelegte Komponenten senken Ausfallrisiko."
],
"correct": 2,
"explanation": "Mehrfach ausgelegte Komponenten senken Ausfallrisiko."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Woran erkennst du Monitoring in einer AP1-Aufgabe?",
"answers": [
"Füllstand und Fehler müssen überwacht werden.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Füllstand und Fehler müssen überwacht werden."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Was ist bei Datenschutz besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Speicher mit personenbezogenen Daten braucht Schutzmaßnahmen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Speicher mit personenbezogenen Daten braucht Schutzmaßnahmen."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Was beschreibt Restore am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Wiederherstellung muss getestet werden."
],
"correct": 2,
"explanation": "Wiederherstellung muss getestet werden."
},
{
"category": "Betrieb & Praxis",
"hint": "Storage in AP1-Situationen bewerten.",
"text": "Welche Aussage zu Dokumentation ist richtig?",
"answers": [
"Volumes, Freigaben und Zuständigkeiten dokumentieren.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Volumes, Freigaben und Zuständigkeiten dokumentieren."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "Thin Clients",
"questions": [
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Was beschreibt Thin Client am besten?",
"answers": [
"Schlanker Arbeitsplatz mit zentral bereitgestellten Anwendungen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Schlanker Arbeitsplatz mit zentral bereitgestellten Anwendungen."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Welche Aussage zu Fat Client ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Leistungsfähiger lokaler Arbeitsplatz mit eigener Verarbeitung.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Leistungsfähiger lokaler Arbeitsplatz mit eigener Verarbeitung."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Woran erkennst du Zentrale Verwaltung in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Updates und Anwendungen werden zentral gepflegt."
],
"correct": 2,
"explanation": "Updates und Anwendungen werden zentral gepflegt."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Was ist bei Serverabhängigkeit besonders wichtig?",
"answers": [
"Thin Clients brauchen zentrale Dienste.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Thin Clients brauchen zentrale Dienste."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Was beschreibt Netzwerkabhängigkeit am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Ohne Netzwerk ist Arbeiten oft eingeschränkt.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Ohne Netzwerk ist Arbeiten oft eingeschränkt."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Welche Aussage zu Lokaler Speicher ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Bei Thin Clients meist geringer oder nicht im Fokus."
],
"correct": 2,
"explanation": "Bei Thin Clients meist geringer oder nicht im Fokus."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Woran erkennst du Energieverbrauch in einer AP1-Aufgabe?",
"answers": [
"Thin Clients können sparsamer sein.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Thin Clients können sparsamer sein."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Was ist bei Rollout besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Zentrale Images vereinfachen Bereitstellung.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Zentrale Images vereinfachen Bereitstellung."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Was beschreibt Wartung am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Weniger lokale Komplexität kann Wartung senken."
],
"correct": 2,
"explanation": "Weniger lokale Komplexität kann Wartung senken."
},
{
"category": "Thin-Client-Grundlagen",
"hint": "Konzept und Unterschiede verstehen.",
"text": "Welche Aussage zu Benutzerprofil ist richtig?",
"answers": [
"Profile werden häufig zentral verwaltet.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Profile werden häufig zentral verwaltet."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Was beschreibt Callcenter am besten?",
"answers": [
"Standardisierte Arbeitsplätze passen oft gut.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Standardisierte Arbeitsplätze passen oft gut."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Welche Aussage zu CAD-Arbeitsplatz ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Hohe lokale Leistung kann gegen Thin Clients sprechen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Hohe lokale Leistung kann gegen Thin Clients sprechen."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Woran erkennst du Ausfallsicherheit in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Server und Netzwerk müssen zuverlässig sein."
],
"correct": 2,
"explanation": "Server und Netzwerk müssen zuverlässig sein."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Was ist bei Datenschutz besonders wichtig?",
"answers": [
"Zentrale Datenhaltung kann Schutz und Kontrolle verbessern.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Zentrale Datenhaltung kann Schutz und Kontrolle verbessern."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Was beschreibt Kosten am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Anschaffung, Betrieb und Serverinfrastruktur zusammen betrachten.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Anschaffung, Betrieb und Serverinfrastruktur zusammen betrachten."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Welche Aussage zu Latenz ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Schlechte Verbindung beeinträchtigt Nutzung."
],
"correct": 2,
"explanation": "Schlechte Verbindung beeinträchtigt Nutzung."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Woran erkennst du Peripherie in einer AP1-Aufgabe?",
"answers": [
"Scanner, Drucker oder Spezialgeräte müssen unterstützt werden.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Scanner, Drucker oder Spezialgeräte müssen unterstützt werden."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Was ist bei Homeoffice besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Verbindung und Sicherheit sind entscheidend.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Verbindung und Sicherheit sind entscheidend."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Was beschreibt Skalierung am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Neue Clients können schnell bereitgestellt werden."
],
"correct": 2,
"explanation": "Neue Clients können schnell bereitgestellt werden."
},
{
"category": "Praxis & Bewertung",
"hint": "Vor- und Nachteile in Szenarien abwägen.",
"text": "Welche Aussage zu AP1-Argumentation ist richtig?",
"answers": [
"Anforderungen bestimmen, ob Thin Client sinnvoll ist.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Anforderungen bestimmen, ob Thin Client sinnvoll ist."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "Netzwerktopologien",
"questions": [
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Was beschreibt Sterntopologie am besten?",
"answers": [
"Alle Endgeräte hängen zentral an Switch oder Verteiler.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Alle Endgeräte hängen zentral an Switch oder Verteiler."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Welche Aussage zu Bustopologie ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Alle Teilnehmer nutzen ein gemeinsames Übertragungsmedium.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Alle Teilnehmer nutzen ein gemeinsames Übertragungsmedium."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Woran erkennst du Ringtopologie in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Teilnehmer sind ringförmig verbunden."
],
"correct": 2,
"explanation": "Teilnehmer sind ringförmig verbunden."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Was ist bei Mesh besonders wichtig?",
"answers": [
"Viele Knoten sind mehrfach miteinander verbunden.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Viele Knoten sind mehrfach miteinander verbunden."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Was beschreibt Baumtopologie am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Hierarchische Struktur aus mehreren Ebenen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Hierarchische Struktur aus mehreren Ebenen."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Welche Aussage zu Zentraler Knoten ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Bei Stern ist der Switch ein kritischer Punkt."
],
"correct": 2,
"explanation": "Bei Stern ist der Switch ein kritischer Punkt."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Woran erkennst du Redundanz in einer AP1-Aufgabe?",
"answers": [
"Mehrfachverbindungen erhöhen Ausfallsicherheit.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Mehrfachverbindungen erhöhen Ausfallsicherheit."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Was ist bei Skalierbarkeit besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Stern- und Baumstrukturen sind oft gut erweiterbar.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Stern- und Baumstrukturen sind oft gut erweiterbar."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Was beschreibt Verkabelungsaufwand am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Mesh kann besonders aufwendig sein."
],
"correct": 2,
"explanation": "Mesh kann besonders aufwendig sein."
},
{
"category": "Topologie-Grundlagen",
"hint": "Strukturen und typische Eigenschaften zuordnen.",
"text": "Welche Aussage zu AP1-Zuordnung ist richtig?",
"answers": [
"Prüfungen fragen oft nach Vor- und Nachteilen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Prüfungen fragen oft nach Vor- und Nachteilen."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Was beschreibt Büro-LAN am besten?",
"answers": [
"Sterntopologie ist in modernen LANs typisch.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Sterntopologie ist in modernen LANs typisch."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Welche Aussage zu Hochverfügbarkeit ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Redundante Verbindungen senken Ausfallrisiko.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Redundante Verbindungen senken Ausfallrisiko."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Woran erkennst du Kosten in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Mehr Redundanz bedeutet oft höhere Kosten."
],
"correct": 2,
"explanation": "Mehr Redundanz bedeutet oft höhere Kosten."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Was ist bei Fehlersuche besonders wichtig?",
"answers": [
"Stern erleichtert oft die Eingrenzung einzelner Leitungen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Stern erleichtert oft die Eingrenzung einzelner Leitungen."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Was beschreibt Single Point of Failure am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Ein zentraler Switch kann ein Ausfallpunkt sein.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Ein zentraler Switch kann ein Ausfallpunkt sein."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Welche Aussage zu Backbone ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Baumstrukturen nutzen oft zentrale Verteilerebenen."
],
"correct": 2,
"explanation": "Baumstrukturen nutzen oft zentrale Verteilerebenen."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Woran erkennst du WLAN-Mesh in einer AP1-Aufgabe?",
"answers": [
"Mesh kann Funkabdeckung verbessern.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Mesh kann Funkabdeckung verbessern."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Was ist bei Dokumentation besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Netzpläne machen Topologien nachvollziehbar.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Netzpläne machen Topologien nachvollziehbar."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Was beschreibt Erweiterung am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Neue Arbeitsplätze brauchen freie Ports und Kabelwege."
],
"correct": 2,
"explanation": "Neue Arbeitsplätze brauchen freie Ports und Kabelwege."
},
{
"category": "Auswahl & Praxis",
"hint": "Topologie passend zu Anforderungen wählen.",
"text": "Welche Aussage zu Prüfungsargumentation ist richtig?",
"answers": [
"Immer Kosten, Ausfallsicherheit und Wartbarkeit abwägen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Immer Kosten, Ausfallsicherheit und Wartbarkeit abwägen."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "VDI & DaaS",
"questions": [
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Was beschreibt VDI am besten?",
"answers": [
"Virtuelle Desktops auf meist eigener Infrastruktur.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Virtuelle Desktops auf meist eigener Infrastruktur."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Welche Aussage zu DaaS ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Desktop as a Service aus einem externen Dienst.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Desktop as a Service aus einem externen Dienst."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Woran erkennst du Virtueller Desktop in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Arbeitsumgebung läuft zentral oder in der Cloud."
],
"correct": 2,
"explanation": "Arbeitsumgebung läuft zentral oder in der Cloud."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Was ist bei Clientgerät besonders wichtig?",
"answers": [
"Dient hauptsächlich als Zugriffspunkt.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Dient hauptsächlich als Zugriffspunkt."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Was beschreibt Zentrale Verwaltung am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Desktops können zentral gepflegt werden.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Desktops können zentral gepflegt werden."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Welche Aussage zu Image ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Vorlage für Desktopbereitstellung."
],
"correct": 2,
"explanation": "Vorlage für Desktopbereitstellung."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Woran erkennst du Persistenter Desktop in einer AP1-Aufgabe?",
"answers": [
"Persönliche Änderungen bleiben erhalten.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Persönliche Änderungen bleiben erhalten."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Was ist bei Nicht-persistenter Desktop besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Desktop wird nach Nutzung zurückgesetzt.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Desktop wird nach Nutzung zurückgesetzt."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Was beschreibt Remote-Protokoll am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Überträgt Bild, Eingabe und Sitzung."
],
"correct": 2,
"explanation": "Überträgt Bild, Eingabe und Sitzung."
},
{
"category": "VDI und DaaS Grundlagen",
"hint": "Virtuelle Desktopmodelle unterscheiden.",
"text": "Welche Aussage zu AP1-Vergleich ist richtig?",
"answers": [
"Eigener Betrieb und Dienstleistung abwägen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Eigener Betrieb und Dienstleistung abwägen."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Was beschreibt Datenschutz am besten?",
"answers": [
"Datenstandort und Auftragsverarbeitung prüfen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Datenstandort und Auftragsverarbeitung prüfen."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Welche Aussage zu Latenz ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Verzögerung beeinflusst Bedienbarkeit.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Verzögerung beeinflusst Bedienbarkeit."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Woran erkennst du Bandbreite in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Viele Desktops brauchen ausreichende Verbindung."
],
"correct": 2,
"explanation": "Viele Desktops brauchen ausreichende Verbindung."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Was ist bei Kostenmodell besonders wichtig?",
"answers": [
"DaaS kann laufende Gebühren statt Investition bedeuten.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "DaaS kann laufende Gebühren statt Investition bedeuten."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Was beschreibt Skalierung am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Cloud-Dienste können flexibel wachsen.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Cloud-Dienste können flexibel wachsen."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Welche Aussage zu Ausfall Internet ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"DaaS ist stark von Verbindung abhängig."
],
"correct": 2,
"explanation": "DaaS ist stark von Verbindung abhängig."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Woran erkennst du Administration in einer AP1-Aufgabe?",
"answers": [
"Zentrale Pflege kann Aufwand senken.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Zentrale Pflege kann Aufwand senken."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Was ist bei Sicherheit besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Zugriff, MFA und Richtlinien sind wichtig.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Zugriff, MFA und Richtlinien sind wichtig."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Was beschreibt Performance am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Grafik- oder Spezialanwendungen brauchen Planung."
],
"correct": 2,
"explanation": "Grafik- oder Spezialanwendungen brauchen Planung."
},
{
"category": "Betrieb & Bewertung",
"hint": "Einsatz anhand von Anforderungen beurteilen.",
"text": "Welche Aussage zu Abwägung ist richtig?",
"answers": [
"Technik, Kosten, Recht und Nutzerbedarf zusammen bewerten.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Technik, Kosten, Recht und Nutzerbedarf zusammen bewerten."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "VLAN",
"questions": [
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Was beschreibt VLAN am besten?",
"answers": [
"Logische Trennung innerhalb eines physischen Netzwerks.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Logische Trennung innerhalb eines physischen Netzwerks."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Welche Aussage zu Broadcast-Domäne ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"VLANs trennen Broadcastbereiche.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "VLANs trennen Broadcastbereiche."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Woran erkennst du VLAN-ID in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Kennzeichnet ein VLAN."
],
"correct": 2,
"explanation": "Kennzeichnet ein VLAN."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Was ist bei Access-Port besonders wichtig?",
"answers": [
"Gehört typischerweise zu einem VLAN.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Gehört typischerweise zu einem VLAN."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Was beschreibt Trunk-Port am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Transportiert mehrere VLANs.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Transportiert mehrere VLANs."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Welche Aussage zu Tagging ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Markiert Frames mit VLAN-Information."
],
"correct": 2,
"explanation": "Markiert Frames mit VLAN-Information."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Woran erkennst du Untagged in einer AP1-Aufgabe?",
"answers": [
"Frames ohne VLAN-Tag am Endgerät.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Frames ohne VLAN-Tag am Endgerät."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Was ist bei Switch besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Setzt VLAN-Zuordnung auf Ports um.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Setzt VLAN-Zuordnung auf Ports um."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Was beschreibt Netztrennung am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Erhöht Struktur und Sicherheit."
],
"correct": 2,
"explanation": "Erhöht Struktur und Sicherheit."
},
{
"category": "VLAN-Grundlagen",
"hint": "Logische Netztrennung verstehen.",
"text": "Welche Aussage zu Gastnetz ist richtig?",
"answers": [
"Typischer VLAN-Einsatzfall.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Typischer VLAN-Einsatzfall."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Was beschreibt Inter-VLAN-Routing am besten?",
"answers": [
"Kommunikation zwischen VLANs braucht Layer-3-Funktion.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Kommunikation zwischen VLANs braucht Layer-3-Funktion."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Welche Aussage zu falsches VLAN ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Endgerät landet im falschen Netz.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Endgerät landet im falschen Netz."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Woran erkennst du Trunk fehlt in einer AP1-Aufgabe?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"VLANs erreichen andere Switches nicht."
],
"correct": 2,
"explanation": "VLANs erreichen andere Switches nicht."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Was ist bei Native VLAN besonders wichtig?",
"answers": [
"Muss bewusst und sicher konfiguriert werden.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Muss bewusst und sicher konfiguriert werden."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Was beschreibt Dokumentation am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"VLAN-IDs und Portzuordnung dokumentieren.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "VLAN-IDs und Portzuordnung dokumentieren."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Welche Aussage zu Sicherheit ist richtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"VLANs ersetzen keine Firewall-Regeln."
],
"correct": 2,
"explanation": "VLANs ersetzen keine Firewall-Regeln."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Woran erkennst du IP-Subnetz in einer AP1-Aufgabe?",
"answers": [
"Jedes VLAN hat oft eigenes Subnetz.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Jedes VLAN hat oft eigenes Subnetz."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Was ist bei DHCP besonders wichtig?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Muss pro VLAN erreichbar sein.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 1,
"explanation": "Muss pro VLAN erreichbar sein."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Was beschreibt Fehleranalyse am besten?",
"answers": [
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung.",
"Portmodus, VLAN-ID und Routing prüfen."
],
"correct": 2,
"explanation": "Portmodus, VLAN-ID und Routing prüfen."
},
{
"category": "VLAN-Praxis",
"hint": "Konfiguration und Fehler bewerten.",
"text": "Welche Aussage zu AP1-Szenario ist richtig?",
"answers": [
"Abteilungstrennung und Gästezugang begründen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Abteilungstrennung und Gästezugang begründen."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "USV - Unterbrechungsfreie Stromversorgung",
"questions": [
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Wofür steht USV?",
"answers": ["Unterbrechungsfreie Stromversorgung", "Universelle Serververwaltung", "Unternehmensweite Softwareverteilung"],
"correct": 0,
"explanation": "Eine USV versorgt Geräte bei Stromproblemen kurzzeitig weiter."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Was ist ein Hauptzweck einer USV?",
"answers": ["Zeit für geordnetes Herunterfahren schaffen", "Speicherplatz erhöhen", "IP-Adressen vergeben"],
"correct": 0,
"explanation": "Eine USV überbrückt Ausfälle und ermöglicht kontrollierte Reaktion."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Welche Störung kann eine USV abfangen?",
"answers": ["Kurzzeitigen Stromausfall", "Falsche Rechtschreibung", "Fehlerhafte SQL-Abfrage automatisch"],
"correct": 0,
"explanation": "USV-Systeme schützen vor Stromausfällen und teils Spannungsschwankungen."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Was ersetzt eine normale USV nicht dauerhaft?",
"answers": ["Langfristige Stromversorgung durch Generator oder Netz", "Ein Patchkabel", "Eine Tastatur"],
"correct": 0,
"explanation": "Eine USV ist meist für Minuten, nicht für endlosen Betrieb ausgelegt."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Welche Systeme werden häufig an eine USV angeschlossen?",
"answers": ["Server, Storage und Netzwerkkomponenten", "Kaffeemaschinen im Pausenraum", "Private Spielekonsolen"],
"correct": 0,
"explanation": "Kritische IT-Infrastruktur soll kontrolliert weiterlaufen oder herunterfahren."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Was ist Autonomiezeit?",
"answers": ["Zeit, die eine USV eine Last versorgen kann", "Zeit bis zur nächsten Mittagspause", "Dauer eines Backups immer in Tagen"],
"correct": 0,
"explanation": "Autonomiezeit hängt von Batterie, Last und Zustand der USV ab."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Warum ist eine USV für Datenbanken sinnvoll?",
"answers": ["Sie reduziert Risiko durch abrupten Stromverlust", "Sie optimiert SQL automatisch", "Sie ersetzt Transaktionen"],
"correct": 0,
"explanation": "Abrupte Ausfälle können Datenverlust oder Inkonsistenzen begünstigen."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Welche Aussage ist korrekt?",
"answers": ["Eine USV schützt nicht vor jedem IT-Risiko", "Eine USV verhindert alle Hackerangriffe", "Eine USV ersetzt Backups"],
"correct": 0,
"explanation": "USV ist Teil eines Schutzkonzepts, aber kein Ersatz für Backups oder Security."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Was sollte bei Stromausfall automatisch passieren können?",
"answers": ["Server geordnet herunterfahren", "Alle Passwörter löschen", "Alle Switches formatieren"],
"correct": 0,
"explanation": "Automatischer Shutdown schützt Systeme und Daten."
},
{
"category": "USV-Grundlagen",
"hint": "Verstehe Zweck, Grenzen und typische Einsatzbereiche einer USV.",
"text": "Was ist ein typischer AP1-Prüfungspunkt zur USV?",
"answers": ["Zweck, Dimensionierung und Shutdown-Konzept erklären", "HTML-Farben auswendig wissen", "Nur die Marke nennen"],
"correct": 0,
"explanation": "AP1 fragt häufig nach praktischer Einordnung und Begründung."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Was muss für die Dimensionierung bekannt sein?",
"answers": ["Leistungsaufnahme der angeschlossenen Geräte", "Lieblingsfarbe des Admins", "Anzahl der Bürofenster"],
"correct": 0,
"explanation": "Die USV muss zur Gesamtlast passen."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Welche Einheit ist bei USV-Angaben häufig?",
"answers": ["VA oder Watt", "Kilometer pro Stunde", "Grad Celsius als Hauptleistung"],
"correct": 0,
"explanation": "USV-Leistung wird häufig in VA und/oder Watt angegeben."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Warum sollte Reserve eingeplant werden?",
"answers": ["Für Lastspitzen, Alterung und spätere Erweiterung", "Damit die USV absichtlich überlastet wird", "Damit Batterien nie geprüft werden"],
"correct": 0,
"explanation": "Reserve macht die Lösung robuster."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Was passiert bei Überlastung einer USV?",
"answers": ["Sie kann abschalten oder die Last nicht zuverlässig versorgen", "Sie erzeugt automatisch mehr Batterien", "Sie wird zu einem Router"],
"correct": 0,
"explanation": "Überlastung gefährdet Schutzwirkung und Betrieb."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Welche Angabe beeinflusst die Laufzeit stark?",
"answers": ["Angeschlossene Last", "Name des Serverraums", "Farbe der Steckdosen"],
"correct": 0,
"explanation": "Je höher die Last, desto kürzer typischerweise die Autonomiezeit."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Was sollte vor Kauf einer USV geprüft werden?",
"answers": ["Anzahl und Art der Anschlüsse", "Nur Verpackungsfarbe", "Ob sie im Flur gut aussieht"],
"correct": 0,
"explanation": "Anschlussart, Leistung und Laufzeit müssen zur Infrastruktur passen."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Warum ist Batteriealterung relevant?",
"answers": ["Kapazität sinkt mit der Zeit", "Batterien werden automatisch schneller", "Alterung verbessert die Laufzeit"],
"correct": 0,
"explanation": "Alternde Batterien verkürzen die tatsächliche Überbrückungszeit."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Was ist bei mehreren Servern wichtig?",
"answers": ["Gesamtlast und Priorisierung beim Shutdown", "Alle Server an eine beliebige Steckdose hängen", "Keine Dokumentation"],
"correct": 0,
"explanation": "Nicht jede Last ist gleich kritisch; Shutdown-Reihenfolge kann wichtig sein."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Welche Planung ist sinnvoll?",
"answers": ["Laufzeit passend zu Shutdown-Zeit plus Reserve wählen", "Laufzeit ignorieren", "Nur billigstes Gerät wählen"],
"correct": 0,
"explanation": "Die USV muss lang genug überbrücken, damit Systeme sauber reagieren."
},
{
"category": "Leistung & Dimensionierung",
"hint": "Dimensioniere USV nach Last, Laufzeit, Reserve und Anschlussbedarf.",
"text": "Was gehört in eine USV-Dokumentation?",
"answers": ["Lasten, Laufzeit, angeschlossene Systeme und Shutdown-Verhalten", "Nur ein Foto", "Private Notizen ohne Bezug"],
"correct": 0,
"explanation": "Diese Angaben helfen Betrieb, Wartung und Störungsreaktion."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Warum sollte eine USV überwacht werden?",
"answers": ["Batteriestatus und Störungen müssen erkannt werden", "Damit niemand sie findet", "Damit Backups gelöscht werden"],
"correct": 0,
"explanation": "Monitoring zeigt Probleme, bevor der Ernstfall kommt."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Warum sind USV-Tests wichtig?",
"answers": ["Sie prüfen, ob Überbrückung und Shutdown funktionieren", "Sie ersetzen jede Wartung", "Sie machen Batterien unendlich haltbar"],
"correct": 0,
"explanation": "Tests zeigen, ob das Konzept praktisch funktioniert."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Was ist bei Batterien zu beachten?",
"answers": ["Sie müssen nach Herstellerangaben geprüft und ersetzt werden", "Sie halten immer ewig", "Sie brauchen keine Beachtung"],
"correct": 0,
"explanation": "Batterien sind Verschleißteile."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Welche Reaktion ist bei USV-Alarm sinnvoll?",
"answers": ["Ursache prüfen und gegebenenfalls Shutdown einleiten", "Alarm ignorieren", "Alle Logs löschen"],
"correct": 0,
"explanation": "Alarme zeigen Handlungsbedarf."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Warum ist Netzwerkkomponente an USV oft sinnvoll?",
"answers": ["Damit Server noch erreichbar und kontrolliert steuerbar bleiben", "Damit Internet schneller wird", "Damit VLANs verschwinden"],
"correct": 0,
"explanation": "Switches und Router können für Shutdown und Verfügbarkeit wichtig sein."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Was ist ein geordneter Shutdown?",
"answers": ["Dienste und Systeme kontrolliert beenden", "Strom sofort hart trennen", "Festplatten absichtlich beschädigen"],
"correct": 0,
"explanation": "Kontrolliertes Herunterfahren reduziert Datenverlust und Schäden."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Was sollte nach einem Stromereignis geprüft werden?",
"answers": ["Logs, Batteriestatus und Systemzustand", "Nur die Wandfarbe", "Nichts"],
"correct": 0,
"explanation": "Nachkontrolle erkennt Folgeschäden oder Wartungsbedarf."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Welche Aussage zur USV und Backup ist richtig?",
"answers": ["USV ersetzt Backups nicht", "USV macht Backups unnötig", "Backups verhindern Stromausfälle"],
"correct": 0,
"explanation": "USV und Backup schützen gegen unterschiedliche Risiken."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Welche USV-Information ist für den Betrieb wichtig?",
"answers": ["Welche Systeme angeschlossen sind", "Welche Musik im Büro läuft", "Welche Mausfarbe genutzt wird"],
"correct": 0,
"explanation": "Betrieb muss wissen, welche Lasten geschützt sind."
},
{
"category": "Betrieb, Wartung & Praxis",
"hint": "Plane Tests, Monitoring, Austausch und Reaktion auf Stromereignisse.",
"text": "Was ist ein typischer Fehler?",
"answers": ["USV installieren, aber Shutdown-Software nie konfigurieren", "Autonomiezeit dokumentieren", "Batterietest einplanen"],
"correct": 0,
"explanation": "Ohne Shutdown-Konfiguration kann die USV ihre Schutzwirkung nur teilweise erfüllen."
}
]
}
@@ -0,0 +1,245 @@
{
"title": "Amortisation",
"questions": [
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Was beschreibt Amortisation am besten?",
"answers": [
"Amortisation hilft, wirtschaftliche Entscheidungen nachvollziehbar zu begründen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Amortisation ist prüfungsrelevant, weil Entscheidungen begründet werden müssen."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Welche Aussage zu Rechenweg ist richtig?",
"answers": [
"Nur das Endergebnis ohne Weg zählt immer.",
"Der Rechenweg muss mit Einheiten und Zwischenschritten nachvollziehbar sein.",
"Einheiten sind grundsätzlich egal."
],
"correct": 1,
"explanation": "IHK-Aufgaben bewerten häufig den nachvollziehbaren Lösungsweg."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Woran erkennst du Kriterien in einer AP1-Aufgabe?",
"answers": [
"Kriterien verhindern jede Entscheidung.",
"Kriterien werden nach der Entscheidung erfunden.",
"Kriterien machen Alternativen vergleichbar."
],
"correct": 2,
"explanation": "Saubere Kriterien machen Entscheidungen transparent."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Was ist bei Kosten besonders wichtig?",
"answers": [
"Kosten müssen vollständig und passend zum Szenario erfasst werden.",
"Kosten spielen in Wirtschaft nie eine Rolle.",
"Nur die höchste Zahl ist relevant."
],
"correct": 0,
"explanation": "Wirtschaftsaufgaben verlangen vollständige Betrachtung."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Was beschreibt Nutzen am besten?",
"answers": [
"Nutzen ist immer verboten.",
"Nutzen kann quantitativ oder qualitativ bewertet werden.",
"Nutzen ist immer nur eine Zufallszahl."
],
"correct": 1,
"explanation": "Nicht jeder Nutzen ist direkt in Euro messbar."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Welche Aussage zu Vergleichbarkeit ist richtig?",
"answers": [
"Jede Alternative nutzt andere Einheiten.",
"Vergleichbarkeit ist nur Dekoration.",
"Alternativen müssen auf derselben Grundlage verglichen werden."
],
"correct": 2,
"explanation": "Ohne gleiche Grundlage ist ein Vergleich unfair."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Woran erkennst du Dokumentation in einer AP1-Aufgabe?",
"answers": [
"Annahmen, Zahlen und Entscheidung müssen dokumentiert werden.",
"Dokumentation macht Rechnungen falsch.",
"Dokumentation ist nur für Grafiken."
],
"correct": 0,
"explanation": "Dokumentation macht Entscheidungen prüfbar."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Was ist bei Prüfungsargumentation besonders wichtig?",
"answers": [
"Eine Begründung ist nie erlaubt.",
"Eine gute Antwort verbindet Rechnung und kurze Begründung.",
"Nur ein Schlagwort reicht immer."
],
"correct": 1,
"explanation": "AP1 fragt häufig nach nachvollziehbarer Bewertung."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Was beschreibt Risiko am besten?",
"answers": [
"Risiken gibt es nur in Netzwerken.",
"Risiken müssen ignoriert werden.",
"Wirtschaftliche Entscheidungen können Risiken und Unsicherheiten enthalten."
],
"correct": 2,
"explanation": "Risiken gehören zu realistischen Entscheidungen."
},
{
"category": "Formel & Rechnung",
"hint": "Amortisation: Formel & Rechnung sicher anwenden.",
"text": "Welche Aussage zu Entscheidung ist richtig?",
"answers": [
"Die beste Alternative hängt von Ziel, Kosten, Nutzen und Rahmenbedingungen ab.",
"Immer gewinnt die billigste Alternative.",
"Immer gewinnt die teuerste Alternative."
],
"correct": 0,
"explanation": "Preis allein reicht oft nicht als Entscheidungskriterium."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Was beschreibt Amortisation am besten?",
"answers": [
"Amortisation hilft, wirtschaftliche Entscheidungen nachvollziehbar zu begründen.",
"Es ist nur Dekoration und hat keinen Prüfungsbezug.",
"Es ist ein zufälliger Begriff ohne technische Bedeutung."
],
"correct": 0,
"explanation": "Amortisation ist prüfungsrelevant, weil Entscheidungen begründet werden müssen."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Welche Aussage zu Rechenweg ist richtig?",
"answers": [
"Nur das Endergebnis ohne Weg zählt immer.",
"Der Rechenweg muss mit Einheiten und Zwischenschritten nachvollziehbar sein.",
"Einheiten sind grundsätzlich egal."
],
"correct": 1,
"explanation": "IHK-Aufgaben bewerten häufig den nachvollziehbaren Lösungsweg."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Woran erkennst du Kriterien in einer AP1-Aufgabe?",
"answers": [
"Kriterien verhindern jede Entscheidung.",
"Kriterien werden nach der Entscheidung erfunden.",
"Kriterien machen Alternativen vergleichbar."
],
"correct": 2,
"explanation": "Saubere Kriterien machen Entscheidungen transparent."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Was ist bei Kosten besonders wichtig?",
"answers": [
"Kosten müssen vollständig und passend zum Szenario erfasst werden.",
"Kosten spielen in Wirtschaft nie eine Rolle.",
"Nur die höchste Zahl ist relevant."
],
"correct": 0,
"explanation": "Wirtschaftsaufgaben verlangen vollständige Betrachtung."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Was beschreibt Nutzen am besten?",
"answers": [
"Nutzen ist immer verboten.",
"Nutzen kann quantitativ oder qualitativ bewertet werden.",
"Nutzen ist immer nur eine Zufallszahl."
],
"correct": 1,
"explanation": "Nicht jeder Nutzen ist direkt in Euro messbar."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Welche Aussage zu Vergleichbarkeit ist richtig?",
"answers": [
"Jede Alternative nutzt andere Einheiten.",
"Vergleichbarkeit ist nur Dekoration.",
"Alternativen müssen auf derselben Grundlage verglichen werden."
],
"correct": 2,
"explanation": "Ohne gleiche Grundlage ist ein Vergleich unfair."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Woran erkennst du Dokumentation in einer AP1-Aufgabe?",
"answers": [
"Annahmen, Zahlen und Entscheidung müssen dokumentiert werden.",
"Dokumentation macht Rechnungen falsch.",
"Dokumentation ist nur für Grafiken."
],
"correct": 0,
"explanation": "Dokumentation macht Entscheidungen prüfbar."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Was ist bei Prüfungsargumentation besonders wichtig?",
"answers": [
"Eine Begründung ist nie erlaubt.",
"Eine gute Antwort verbindet Rechnung und kurze Begründung.",
"Nur ein Schlagwort reicht immer."
],
"correct": 1,
"explanation": "AP1 fragt häufig nach nachvollziehbarer Bewertung."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Was beschreibt Risiko am besten?",
"answers": [
"Risiken gibt es nur in Netzwerken.",
"Risiken müssen ignoriert werden.",
"Wirtschaftliche Entscheidungen können Risiken und Unsicherheiten enthalten."
],
"correct": 2,
"explanation": "Risiken gehören zu realistischen Entscheidungen."
},
{
"category": "Bewertung",
"hint": "Amortisation: Bewertung sicher anwenden.",
"text": "Welche Aussage zu Entscheidung ist richtig?",
"answers": [
"Die beste Alternative hängt von Ziel, Kosten, Nutzen und Rahmenbedingungen ab.",
"Immer gewinnt die billigste Alternative.",
"Immer gewinnt die teuerste Alternative."
],
"correct": 0,
"explanation": "Preis allein reicht oft nicht als Entscheidungskriterium."
}
]
}

Some files were not shown because too many files have changed in this diff Show More