Magento 2 Experten — Hyvä Theme, Tailwind CSS & SEO aus einer Hand ›

Produktbilder und Lagerbestand korrekt anzeigen

Produktbilder und Lagerbestand korrekt anzeigen

~14 Min. Lesezeit Zuletzt aktualisiert am 8. August 2026

Zwei praktisch wichtige Datenpunkte fehlen noch: ein echtes Produktbild und der aktuelle Lagerbestand – dieselben API-Felder wie im React-Web-Tutorial, hier dargestellt mit React Natives <Image>-Komponente.

Die vollständige Bild-URL zusammensetzen

api/magentoApi.js
// ... vorheriger Code ...

const MEDIA_BASE_URL = process.env.EXPO_PUBLIC_MAGENTO_MEDIA_URL;

export function ermittleProduktbild(produkt) {
  const hauptbild = produkt.media_gallery_entries?.find((eintrag) =>
    eintrag.types?.includes('image')
  );
  const irgendeinBild = produkt.media_gallery_entries?.[0];
  const eintrag = hauptbild ?? irgendeinBild;

  if (!eintrag) {
    return null;
  }

  return `${MEDIA_BASE_URL}/catalog/product${eintrag.file}`;
}

export function ermittleLagerbestand(produkt) {
  const stockItem = produkt.extension_attributes?.stock_item;
  return {
    aufLager: stockItem?.is_in_stock ?? false,
    menge: stockItem?.qty ?? 0,
  };
}

Diese beiden Funktionen sind – genau wie leseCustomAttribute() in Kapitel 10 – praktisch IDENTISCH zum React-Web-Tutorial. Der einzige Unterschied: MEDIA_BASE_URL kommt hier aus process.env.EXPO_PUBLIC_... statt import.meta.env.VITE_....

ProductDetailScreen.js: Bild und Bestand integrieren

screens/ProductDetailScreen.js
import { useEffect, useState } from 'react';
import { ScrollView, Text, Image, ActivityIndicator, StyleSheet } from 'react-native';
import {
  fetchProductBySku,
  leseCustomAttribute,
  ermittleProduktbild,
  ermittleLagerbestand,
} from '../api/magentoApi';

export default function ProductDetailScreen({ route }) {
  const { sku } = route.params;
  const [produkt, setProdukt] = useState(null);
  const [ladend, setLadend] = useState(true);

  useEffect(() => {
    setLadend(true);
    async function laden() {
      const data = await fetchProductBySku(sku);
      setProdukt(data);
      setLadend(false);
    }
    laden();
  }, [sku]);

  if (ladend) {
    return <ActivityIndicator style={styles.zentriert} size="large" />;
  }

  const beschreibung = leseCustomAttribute(produkt, 'description');
  const bildUrl = ermittleProduktbild(produkt);
  const { aufLager, menge } = ermittleLagerbestand(produkt);

  return (
    <ScrollView style={styles.container}>
      {bildUrl && (
        <Image source={{ uri: bildUrl }} style={styles.bild} resizeMode="contain" />
      )}
      <Text style={styles.titel}>{produkt.name}</Text>
      <Text>SKU: {produkt.sku}</Text>
      <Text>{produkt.price} €</Text>
      <Text>
        {aufLager ? `Auf Lager (${menge} Stück)` : 'Ausverkauft'}
      </Text>
      {beschreibung && <Text style={styles.beschreibung}>{beschreibung}</Text>}
    </ScrollView>
  );
}

const styles = StyleSheet.create({
  zentriert: { flex: 1, justifyContent: 'center' },
  container: { padding: 16 },
  bild: { width: '100%', height: 250, marginBottom: 16 },
  titel: { fontSize: 20, fontWeight: 'bold', marginBottom: 8 },
  beschreibung: { marginTop: 16 },
});

Achtung: React Natives <Image> BRAUCHT eine explizite width/height im style (anders als HTML <img>, das ohne Größenangabe die natürliche Bildgröße nutzt) – ohne diese Angaben rendert das Bild gar nicht oder mit Größe 0.

Tipp: Damit zeigt der Detail-Screen jetzt WIRKLICH alle wesentlichen Produktdaten: Bild, Name, SKU, Preis, Lagerbestand und Beschreibung – testen Sie das mit mehreren Ihrer echten Produkte, idealerweise auf einem echten Gerät via Expo Go, um zu prüfen, wie Bilder tatsächlich über eine mobile Verbindung laden.