Plugin Directory

Changeset 3431054


Ignore:
Timestamp:
01/02/2026 01:22:32 PM (7 weeks ago)
Author:
artidomo
Message:

Version 2.0.0 - Add full English and German translations

  • Added complete internationalization (i18n) support
  • Created POT template file for translators
  • Added German (de_DE) translation files (.po/.mo)
  • Updated readme.txt to English (primary) with German notice
  • Plugin UI now displays in German when WordPress uses de_DE locale
Location:
artidomo-print-on-demand/trunk
Files:
4 added
7 deleted
4 edited

Legend:

Unmodified
Added
Removed
  • artidomo-print-on-demand/trunk/admin/class-admin-interface.php

    r3430729 r3431054  
    22/**
    33 * Admin Interface Class
    4  * Produktzuordnung und Einstellungen im WordPress Admin
     4 * Product mapping and settings in WordPress Admin
    55 */
    66
     
    1717        $instance = new self();
    1818
    19         // WooCommerce Product Data Tab (statt Sidebar Meta Box!)
     19        // WooCommerce Product Data Tab
    2020        add_filter('woocommerce_product_data_tabs', array($instance, 'add_artidomo_product_tab'));
    2121        add_action('woocommerce_product_data_panels', array($instance, 'render_artidomo_product_panel'));
     
    4343
    4444    /**
    45      * Füge artidomo Tab zu WooCommerce Product Data hinzu
    46      * NUR für Simple/Grouped/External Products - NICHT für Variable Products!
    47      * (Bei Variable Products erfolgt die Zuordnung auf Varianten-Ebene)
     45     * Add artidomo tab to WooCommerce Product Data
    4846     */
    4947    public function add_artidomo_product_tab($tabs) {
    5048        $tabs['artidomo'] = array(
    51             'label'    => __('artidomo', 'artidomo-connector'),
     49            'label'    => __('artidomo', 'artidomo-print-on-demand'),
    5250            'target'   => 'artidomo_product_data',
    5351            'class'    => array('show_if_simple', 'show_if_grouped', 'show_if_external'),
     
    6866                woocommerce_wp_text_input(array(
    6967                    'id'          => '_artidomo_sku',
    70                     'label'       => __('artidomo SKU', 'artidomo-connector'),
    71                     'placeholder' => 'z.B. A001-POSTER',
     68                    'label'       => __('artidomo SKU', 'artidomo-print-on-demand'),
     69                    /* translators: Example SKU format */
     70                    'placeholder' => __('e.g. A001-POSTER', 'artidomo-print-on-demand'),
    7271                    'desc_tip'    => true,
    73                     'description' => __('Die SKU des Produkts im artidomo System', 'artidomo-connector'),
     72                    'description' => __('The SKU of the product in the artidomo system', 'artidomo-print-on-demand'),
    7473                    'value'       => get_post_meta($post->ID, '_artidomo_sku', true),
    7574                ));
     
    7776                woocommerce_wp_text_input(array(
    7877                    'id'          => '_artidomo_printfilename',
    79                     'label'       => __('Druckdatei', 'artidomo-connector'),
     78                    'label'       => __('Print file', 'artidomo-print-on-demand'),
    8079                    'placeholder' => 'design-001.pdf',
    8180                    'desc_tip'    => true,
    82                     'description' => __('Dateiname der Druckdatei', 'artidomo-connector'),
     81                    'description' => __('Filename of the print file', 'artidomo-print-on-demand'),
    8382                    'value'       => get_post_meta($post->ID, '_artidomo_printfilename', true),
    8483                ));
    85 
    86                 // Info: Dateiquelle wird automatisch auf "Druckfilezuordnung" gesetzt
    8784                ?>
    8885                <p class="form-field" style="padding-left: 12px;">
    8986                    <em style="color: #666;">
    90                         ℹ️ Dateiquelle: <strong>Druckfilezuordnung</strong> (automatisch für WooCommerce)
     87                        ℹ️ <?php esc_html_e('File source:', 'artidomo-print-on-demand'); ?> <strong><?php esc_html_e('Print file mapping', 'artidomo-print-on-demand'); ?></strong> (<?php esc_html_e('automatic for WooCommerce', 'artidomo-print-on-demand'); ?>)
    9188                    </em>
    9289                </p>
    9390                <?php
    94 
    95                 // Hinweis für variable Produkte
    9691                $product = wc_get_product($post->ID);
    9792                if ($product && $product->is_type('variable')):
     
    9994                <p class="form-field" style="padding-left: 12px;">
    10095                    <em style="color: #666;">
    101                         ℹ️ Bei variablen Produkten kann jede Variante eigene Zuordnungen haben.
    102                         Diese Werte gelten nur wenn Varianten keine eigenen haben.
     96                        ℹ️ <?php esc_html_e('For variable products, each variation can have its own mappings. These values only apply if variations have no own mappings.', 'artidomo-print-on-demand'); ?>
    10397                    </em>
    10498                </p>
     
    110104
    111105    /**
    112      * Speichere artidomo Product Data
     106     * Save artidomo Product Data
    113107     */
    114108    public function save_artidomo_product_data($post_id) {
    115         // Security Checks
    116109        if (defined('DOING_AUTOSAVE') && DOING_AUTOSAVE) {
    117110            return;
     
    122115        }
    123116
    124         // Speichere Felder
    125117        if (isset($_POST['_artidomo_sku'])) {
    126118            update_post_meta($post_id, '_artidomo_sku', sanitize_text_field($_POST['_artidomo_sku']));
    127             // Automatisch "Druckfilezuordnung" setzen für WooCommerce
    128119            update_post_meta($post_id, '_artidomo_personalization_provider', 'Druckfilezuordnung');
    129120        } else {
     
    140131
    141132    /**
    142      * Füge Felder zu Variationen hinzu
     133     * Add fields to variations
    143134     */
    144135    public function add_variation_fields($loop, $variation_data, $variation) {
     
    147138        $artidomo_sku = get_post_meta($variation_id, '_artidomo_sku', true);
    148139        $printfilename = get_post_meta($variation_id, '_artidomo_printfilename', true);
    149         $personalization_provider = get_post_meta($variation_id, '_artidomo_personalization_provider', true);
    150140
    151141        ?>
    152142        <div class="form-row form-row-full artidomo-variation-fields">
    153143            <h4 style="margin-top: 20px; padding-top: 20px; border-top: 1px solid #ddd;">
    154                 artidomo Zuordnung
     144                <?php esc_html_e('artidomo Mapping', 'artidomo-print-on-demand'); ?>
    155145            </h4>
    156146
    157147            <p class="form-field">
    158                 <label>artidomo SKU:</label>
     148                <label><?php esc_html_e('artidomo SKU:', 'artidomo-print-on-demand'); ?></label>
    159149                <input type="text"
    160                        name="artidomo_sku[<?php echo $loop; ?>]"
     150                       name="artidomo_sku[<?php echo esc_attr($loop); ?>]"
    161151                       value="<?php echo esc_attr($artidomo_sku); ?>"
    162                        placeholder="z.B. A001-POSTER">
     152                       placeholder="<?php esc_attr_e('e.g. A001-POSTER', 'artidomo-print-on-demand'); ?>">
    163153            </p>
    164154
    165155            <p class="form-field">
    166                 <label>Druckdatei:</label>
     156                <label><?php esc_html_e('Print file:', 'artidomo-print-on-demand'); ?></label>
    167157                <input type="text"
    168                        name="artidomo_printfilename[<?php echo $loop; ?>]"
     158                       name="artidomo_printfilename[<?php echo esc_attr($loop); ?>]"
    169159                       value="<?php echo esc_attr($printfilename); ?>"
    170160                       placeholder="design-001.pdf">
     
    172162
    173163            <p class="form-field">
    174                 <em style="color: #666;">ℹ️ Dateiquelle: <strong>Druckfilezuordnung</strong> (automatisch)</em>
     164                <em style="color: #666;">ℹ️ <?php esc_html_e('File source:', 'artidomo-print-on-demand'); ?> <strong><?php esc_html_e('Print file mapping', 'artidomo-print-on-demand'); ?></strong> (<?php esc_html_e('automatic', 'artidomo-print-on-demand'); ?>)</em>
    175165            </p>
    176166        </div>
     
    179169
    180170    /**
    181      * Speichere Variation Fields
     171     * Save Variation Fields
    182172     */
    183173    public function save_variation_fields($variation_id, $loop) {
     
    185175            $sku = sanitize_text_field($_POST['artidomo_sku'][$loop]);
    186176            update_post_meta($variation_id, '_artidomo_sku', $sku);
    187             // Automatisch "Druckfilezuordnung" setzen für WooCommerce
    188177            if (!empty($sku)) {
    189178                update_post_meta($variation_id, '_artidomo_personalization_provider', 'Druckfilezuordnung');
     
    197186
    198187    /**
    199      * Füge Spalten zur Produktliste hinzu
     188     * Add columns to product list
    200189     */
    201190    public function add_product_columns($columns) {
    202         // Füge vor der letzten Spalte (Datum) ein
    203191        $new_columns = array();
    204192
     
    237225
    238226    /**
    239      * Füge Bulk Actions hinzu
     227     * Add Bulk Actions
    240228     */
    241229    public function add_bulk_actions($actions) {
    242         $actions['artidomo_export_selected'] = 'artidomo: Exportieren';
     230        $actions['artidomo_export_selected'] = __('artidomo: Export', 'artidomo-print-on-demand');
    243231        return $actions;
    244232    }
     
    252240        }
    253241
    254         // TODO: Implementiere selektiven Export
    255         // Aktuell: Redirect zur normalen Export-Funktion
    256 
    257242        return add_query_arg('artidomo_bulk_export', count($post_ids), $redirect_to);
    258243    }
    259244
    260245    /**
    261      * Füge Settings Submenu hinzu
     246     * Add Settings Submenu
    262247     */
    263248    public function add_settings_submenu() {
    264249        add_submenu_page(
    265250            'woocommerce',
    266             'artidomo CSV Import/Export',
    267             'artidomo CSV',
     251            __('artidomo CSV Import/Export', 'artidomo-print-on-demand'),
     252            __('artidomo CSV', 'artidomo-print-on-demand'),
    268253            'manage_woocommerce',
    269254            'artidomo-csv',
     
    276261     */
    277262    public function render_csv_page() {
    278         // Import Success Message
    279263        if (isset($_GET['import']) && $_GET['import'] === 'success') {
    280264            $imported = isset($_GET['imported']) ? intval($_GET['imported']) : 0;
     
    282266            ?>
    283267            <div class="notice notice-success is-dismissible">
    284                 <p><strong>✅ Import erfolgreich!</strong></p>
    285                 <p><?php echo $imported; ?> Produkte importiert.
    286                    <?php if ($errors > 0): ?>
    287                        (<?php echo $errors; ?> Fehler)
    288                    <?php endif; ?>
     268                <p><strong>✅ <?php esc_html_e('Import successful!', 'artidomo-print-on-demand'); ?></strong></p>
     269                <p>
     270                    <?php
     271                    /* translators: %d: number of products imported */
     272                    printf(esc_html__('%d products imported.', 'artidomo-print-on-demand'), $imported);
     273                    if ($errors > 0) {
     274                        /* translators: %d: number of errors */
     275                        printf(' (' . esc_html__('%d errors', 'artidomo-print-on-demand') . ')', $errors);
     276                    }
     277                    ?>
    289278                </p>
    290279            </div>
     
    292281        }
    293282
    294         // Statistiken
    295283        $stats = Artidomo_CSV_Handler::get_statistics();
    296 
    297284        ?>
    298285        <div class="wrap">
    299             <h1>artidomo CSV Import/Export</h1>
    300 
    301             <!-- Statistiken -->
     286            <h1><?php esc_html_e('artidomo CSV Import/Export', 'artidomo-print-on-demand'); ?></h1>
     287
     288            <!-- Statistics -->
    302289            <div class="artidomo-stats-box" style="background: #f9f9f9; padding: 20px; margin: 20px 0; border-radius: 5px;">
    303                 <h2>📊 Statistiken</h2>
    304                 <p><strong><?php echo $stats['total_all']; ?></strong> Produkte/Varianten gesamt</p>
    305                 <p><strong><?php echo $stats['total_mapped']; ?></strong> davon mit artidomo SKU zugeordnet</p>
    306                 <p><strong><?php echo $stats['with_printfile']; ?></strong> davon mit Druckdatei</p>
     290                <h2>📊 <?php esc_html_e('Statistics', 'artidomo-print-on-demand'); ?></h2>
     291                <p><strong><?php echo esc_html($stats['total_all']); ?></strong> <?php esc_html_e('products/variations total', 'artidomo-print-on-demand'); ?></p>
     292                <p><strong><?php echo esc_html($stats['total_mapped']); ?></strong> <?php esc_html_e('mapped with artidomo SKU', 'artidomo-print-on-demand'); ?></p>
     293                <p><strong><?php echo esc_html($stats['with_printfile']); ?></strong> <?php esc_html_e('with print file', 'artidomo-print-on-demand'); ?></p>
    307294            </div>
    308295
    309             <!-- 3-Spalten Layout für Export, Import und Info -->
     296            <!-- 3-Column Layout -->
    310297            <div style="display: grid; grid-template-columns: repeat(3, 1fr); gap: 20px; margin: 20px 0;">
    311298
    312299                <!-- Export -->
    313300                <div class="artidomo-export-box" style="background: white; padding: 20px; border: 1px solid #ddd; border-radius: 5px;">
    314                     <h2 style="margin-top: 0;">📤 Export</h2>
    315                     <p>Exportiere alle Produktzuordnungen als CSV-Datei.</p>
    316 
    317                     <form method="post" action="<?php echo admin_url('admin-post.php'); ?>">
     301                    <h2 style="margin-top: 0;">📤 <?php esc_html_e('Export', 'artidomo-print-on-demand'); ?></h2>
     302                    <p><?php esc_html_e('Export all product mappings as CSV file.', 'artidomo-print-on-demand'); ?></p>
     303
     304                    <form method="post" action="<?php echo esc_url(admin_url('admin-post.php')); ?>">
    318305                        <?php wp_nonce_field('artidomo_export_csv'); ?>
    319306                        <input type="hidden" name="action" value="artidomo_export_csv">
    320307                        <button type="submit" class="button button-primary">
    321                             CSV exportieren (<?php echo $stats['total_all']; ?> Produkte)
     308                            <?php
     309                            /* translators: %d: number of products */
     310                            printf(esc_html__('Export CSV (%d products)', 'artidomo-print-on-demand'), $stats['total_all']);
     311                            ?>
    322312                        </button>
    323313                    </form>
     
    326316                <!-- Import -->
    327317                <div class="artidomo-import-box" style="background: white; padding: 20px; border: 1px solid #ddd; border-radius: 5px;">
    328                     <h2 style="margin-top: 0;">📥 Import</h2>
    329                     <p>Importiere Produktzuordnungen aus einer CSV-Datei.</p>
     318                    <h2 style="margin-top: 0;">📥 <?php esc_html_e('Import', 'artidomo-print-on-demand'); ?></h2>
     319                    <p><?php esc_html_e('Import product mappings from a CSV file.', 'artidomo-print-on-demand'); ?></p>
    330320
    331321                    <div class="notice notice-info inline" style="margin: 10px 0;">
    332                         <p style="margin: 5px 0;"><strong>ℹ️ CSV Format:</strong></p>
     322                        <p style="margin: 5px 0;"><strong>ℹ️ <?php esc_html_e('CSV Format:', 'artidomo-print-on-demand'); ?></strong></p>
    333323                        <ul style="list-style: disc; margin-left: 20px; font-size: 12px;">
    334                             <li>Semikolon-getrennt (;)</li>
    335                             <li>UTF-8 Kodierung</li>
    336                             <li>Header-Zeile erforderlich</li>
     324                            <li><?php esc_html_e('Semicolon-separated (;)', 'artidomo-print-on-demand'); ?></li>
     325                            <li><?php esc_html_e('UTF-8 encoding', 'artidomo-print-on-demand'); ?></li>
     326                            <li><?php esc_html_e('Header row required', 'artidomo-print-on-demand'); ?></li>
    337327                        </ul>
    338328                    </div>
    339329
    340330                    <form method="post"
    341                           action="<?php echo admin_url('admin-post.php'); ?>"
     331                          action="<?php echo esc_url(admin_url('admin-post.php')); ?>"
    342332                          enctype="multipart/form-data">
    343333                        <?php wp_nonce_field('artidomo_import_csv'); ?>
     
    348338                        </p>
    349339
    350                         <button type="submit" class="button button-primary">CSV importieren</button>
     340                        <button type="submit" class="button button-primary"><?php esc_html_e('Import CSV', 'artidomo-print-on-demand'); ?></button>
    351341                    </form>
    352342                </div>
    353343
    354                 <!-- Info: Portal-Zuordnung (NEU!) -->
     344                <!-- Info -->
    355345                <div class="artidomo-info-box" style="background: #fff3cd; padding: 20px; border: 1px solid #ffc107; border-radius: 5px;">
    356                     <h2 style="margin-top: 0; color: #856404;">💡 Empfehlung</h2>
     346                    <h2 style="margin-top: 0; color: #856404;">💡 <?php esc_html_e('Recommendation', 'artidomo-print-on-demand'); ?></h2>
    357347                    <p style="font-size: 14px; line-height: 1.6;">
    358                         <strong>Produktzuordnungen im Portal verwalten!</strong>
     348                        <strong><?php esc_html_e('Manage product mappings in the Portal!', 'artidomo-print-on-demand'); ?></strong>
    359349                    </p>
    360350                    <p style="font-size: 13px; color: #856404; line-height: 1.5;">
    361                         Hier in WooCommerce können Zuordnungen manuell gesetzt werden, aber es besteht die Gefahr von Fehlern.
     351                        <?php esc_html_e('Mappings can be set manually here in WooCommerce, but there is a risk of errors.', 'artidomo-print-on-demand'); ?>
    362352                    </p>
    363353                    <p style="font-size: 13px; color: #856404; line-height: 1.5; margin-bottom: 15px;">
    364                         <strong>Besser:</strong> Nutze die zentrale Produktverwaltung im artidomo Portal unter <em>Shop-Verbindungen → Produktzuordnung</em>.
     354                        <strong><?php esc_html_e('Better:', 'artidomo-print-on-demand'); ?></strong> <?php esc_html_e('Use the central product management in the artidomo Portal under Shop Connections → Product Mapping.', 'artidomo-print-on-demand'); ?>
    365355                    </p>
    366356                    <a href="https://portal.artidomo.eu/shops" target="_blank" class="button button-secondary" style="width: 100%; text-align: center;">
    367                         Zum Portal
     357                        <?php esc_html_e('Go to Portal', 'artidomo-print-on-demand'); ?>
    368358                    </a>
    369359                </div>
     
    378368     */
    379369    public function enqueue_admin_assets($hook) {
    380         // Nur auf relevanten Seiten
    381370        if (!in_array($hook, array('post.php', 'post-new.php', 'edit.php', 'woocommerce_page_artidomo-connection', 'woocommerce_page_artidomo-csv'))) {
    382371            return;
    383372        }
    384373
    385         // Inline CSS
    386374        wp_add_inline_style('wp-admin', '
    387375            .artidomo-variation-fields input[type="text"],
  • artidomo-print-on-demand/trunk/artidomo-print.php

    r3430729 r3431054  
    6767    <div class="notice notice-error">
    6868        <p>
    69             <strong>artidomo Print on Demand</strong> benötigt WooCommerce.
    70             Bitte installiere und aktiviere <a href="<?php echo admin_url('plugin-install.php?s=woocommerce&tab=search&type=term'); ?>">WooCommerce</a> zuerst.
     69            <strong>artidomo Print on Demand</strong> <?php esc_html_e('requires WooCommerce. Please install and activate', 'artidomo-print-on-demand'); ?>
     70            <a href="<?php echo esc_url(admin_url('plugin-install.php?s=woocommerce&tab=search&type=term')); ?>">WooCommerce</a> <?php esc_html_e('first.', 'artidomo-print-on-demand'); ?>
    7171        </p>
    7272    </div>
     
    8282    }
    8383});
     84
     85/**
     86 * Load plugin text domain for translations
     87 */
     88function artidomo_pod_load_textdomain() {
     89    load_plugin_textdomain(
     90        'artidomo-print-on-demand',
     91        false,
     92        dirname(ARTIDOMO_POD_PLUGIN_BASENAME) . '/languages'
     93    );
     94}
     95add_action('init', 'artidomo_pod_load_textdomain');
    8496
    8597/**
     
    120132        deactivate_plugins(ARTIDOMO_POD_PLUGIN_BASENAME);
    121133        wp_die(
    122             'artidomo Print on Demand benötigt WooCommerce. Bitte installiere WooCommerce zuerst.',
    123             'Plugin Activation Error',
     134            esc_html__('artidomo Print on Demand requires WooCommerce. Please install WooCommerce first.', 'artidomo-print-on-demand'),
     135            esc_html__('Plugin Activation Error', 'artidomo-print-on-demand'),
    124136            array('back_link' => true)
    125137        );
  • artidomo-print-on-demand/trunk/includes/class-one-click-connect.php

    r3430729 r3431054  
    22/**
    33 * One-Click Connect Class
    4  * Implementiert Token-basierte Verbindung zwischen WooCommerce Shop und artidomo Backend
     4 * Implements token-based connection between WooCommerce Shop and artidomo Backend
    55 */
    66
     
    1717        $instance = new self();
    1818
    19         // REST API Endpoint für Connection Callback
     19        // REST API Endpoint for Connection Callback
    2020        add_action('rest_api_init', array($instance, 'register_rest_routes'));
    2121
    22         // Admin Menu für manuelle Verbindung
     22        // Admin Menu for manual connection
    2323        add_action('admin_menu', array($instance, 'add_connection_page'));
    2424        add_action('admin_menu', array($instance, 'add_all_mappings_page'));
    2525
    26         // AJAX Handler für Token-Validierung
     26        // AJAX Handler for Token Validation
    2727        add_action('wp_ajax_artidomo_validate_token', array($instance, 'ajax_validate_token'));
    2828
    29         // Admin Post Handler für Disconnect (Form Submission)
     29        // Admin Post Handler for Disconnect (Form Submission)
    3030        add_action('admin_post_artidomo_disconnect', array($instance, 'admin_post_disconnect'));
    3131    }
    3232
    3333    /**
    34      * Registriere REST API Routes für One-Click Connect
     34     * Register REST API Routes for One-Click Connect
    3535     */
    3636    public function register_rest_routes() {
     
    5555
    5656    /**
    57      * Verifiziere Connect Request Signatur
     57     * Verify Connect Request Signature
    5858     */
    5959    public function verify_connect_signature($request) {
     
    6363            return new WP_Error(
    6464                'missing_token',
    65                 'Token fehlt',
     65                __('Token missing', 'artidomo-print-on-demand'),
    6666                array('status' => 400)
    6767            );
    6868        }
    6969
    70         // Token wird vom Backend signiert - validiere über Backend API
    71         return true; // Backend validiert im handle_connect_request
    72     }
    73 
    74     /**
    75      * Verifiziere Disconnect Permission
     70        // Token is signed by backend - validate via Backend API
     71        return true; // Backend validates in handle_connect_request
     72    }
     73
     74    /**
     75     * Verify Disconnect Permission
    7676     */
    7777    public function verify_disconnect_permission($request) {
     
    8080
    8181    /**
    82      * Handle Connection Request vom artidomo Backend
     82     * Handle Connection Request from artidomo Backend
    8383     */
    8484    public function handle_connect_request($request) {
     
    8888            return new WP_Error(
    8989                'missing_token',
    90                 'Token fehlt',
     90                __('Token missing', 'artidomo-print-on-demand'),
    9191                array('status' => 400)
    9292            );
    9393        }
    9494
    95         // Validiere Token über Backend API
     95        // Validate Token via Backend API
    9696        $response = wp_remote_post(ARTIDOMO_API_URL . '/woocommerce/validate-connection-token', array(
    9797            'headers' => array('Content-Type' => 'application/json'),
     
    106106            return new WP_Error(
    107107                'api_error',
    108                 'Verbindung zum artidomo Backend fehlgeschlagen: ' . $response->get_error_message(),
     108                /* translators: %s: error message */
     109                sprintf(__('Connection to artidomo backend failed: %s', 'artidomo-print-on-demand'), $response->get_error_message()),
    109110                array('status' => 500)
    110111            );
     
    117118            return new WP_Error(
    118119                'invalid_token',
    119                 $body['error'] ?? 'Token ungültig oder abgelaufen',
     120                $body['error'] ?? __('Token invalid or expired', 'artidomo-print-on-demand'),
    120121                array('status' => 401)
    121122            );
    122123        }
    123124
    124         // ✨ NEUE LOGIK: Generiere WooCommerce REST API Keys lokal im Shop
     125        // Generate WooCommerce REST API Keys locally in the shop
    125126        $api_keys = $this->create_woocommerce_api_keys();
    126127
    127128        if (is_wp_error($api_keys)) {
    128             return $api_keys; // Fehler zurückgeben
    129         }
    130 
    131         // Generiere Webhook Secret
     129            return $api_keys; // Return error
     130        }
     131
     132        // Generate Webhook Secret
    132133        $webhook_secret = wp_generate_password(32, false);
    133134
    134         // ✨ Sende Credentials AN das Backend (nicht umgekehrt!)
     135        // Send Credentials TO the Backend (not the other way around!)
    135136        $credentials_response = wp_remote_post(ARTIDOMO_API_URL . '/woocommerce/exchange-token', array(
    136137            'headers' => array('Content-Type' => 'application/json'),
     
    138139                'token' => $token,
    139140                'shop_url' => get_site_url(),
    140                 'consumer_key' => $api_keys['consumer_key'],        // ✅ JETZT MITGESENDET!
    141                 'consumer_secret' => $api_keys['consumer_secret'],  // ✅ JETZT MITGESENDET!
     141                'consumer_key' => $api_keys['consumer_key'],
     142                'consumer_secret' => $api_keys['consumer_secret'],
    142143                'webhook_secret' => $webhook_secret
    143144            )),
     
    148149            return new WP_Error(
    149150                'backend_error',
    150                 'Fehler beim Speichern im Backend: ' . $credentials_response->get_error_message(),
     151                /* translators: %s: error message */
     152                sprintf(__('Error saving to backend: %s', 'artidomo-print-on-demand'), $credentials_response->get_error_message()),
    151153                array('status' => 500)
    152154            );
     
    159161            return new WP_Error(
    160162                'backend_failed',
    161                 $credentials_body['error'] ?? 'Backend konnte Shop nicht erstellen',
     163                $credentials_body['error'] ?? __('Backend could not create shop', 'artidomo-print-on-demand'),
    162164                array('status' => 500)
    163165            );
    164166        }
    165167
    166         // Speichere Credentials lokal
     168        // Save Credentials locally
    167169        update_option('artidomo_connected', true);
    168170        update_option('artidomo_shop_id', sanitize_text_field($credentials_body['shop_id']));
     
    173175        update_option('artidomo_connected_at', current_time('mysql'));
    174176
    175         // Registriere Webhooks automatisch
     177        // Register Webhooks automatically
    176178        $this->register_webhooks($webhook_secret);
    177179
    178180        return rest_ensure_response(array(
    179181            'success' => true,
    180             'message' => 'Verbindung erfolgreich hergestellt',
     182            'message' => __('Connection established successfully', 'artidomo-print-on-demand'),
    181183            'shop_url' => get_site_url(),
    182184            'connected_at' => current_time('mysql'),
     
    185187
    186188    /**
    187      * Erstelle WooCommerce REST API Keys programmatisch
     189     * Create WooCommerce REST API Keys programmatically
    188190     */
    189191    private function create_woocommerce_api_keys() {
    190192        global $wpdb;
    191193
    192         // Prüfe ob WooCommerce aktiv ist
     194        // Check if WooCommerce is active
    193195        if (!class_exists('WooCommerce')) {
    194196            return new WP_Error(
    195197                'woocommerce_missing',
    196                 'WooCommerce ist nicht installiert oder aktiviert',
     198                __('WooCommerce is not installed or activated', 'artidomo-print-on-demand'),
    197199                array('status' => 500)
    198200            );
    199201        }
    200202
    201         // Hole Admin User ID (für REST API Calls ohne eingeloggten User)
    202         // get_current_user_id() ist 0 bei REST API Calls!
     203        // Get Admin User ID (for REST API Calls without logged in user)
     204        // get_current_user_id() is 0 for REST API Calls!
    203205        $user_id = get_current_user_id();
    204206        if ($user_id === 0) {
    205             // Finde ersten Administrator
     207            // Find first Administrator
    206208            $admin_users = get_users(array(
    207209                'role' => 'administrator',
     
    214216                return new WP_Error(
    215217                    'no_admin_user',
    216                     'Kein Administrator-Account gefunden',
     218                    __('No administrator account found', 'artidomo-print-on-demand'),
    217219                    array('status' => 500)
    218220                );
     
    222224        }
    223225
    224         // Generiere Consumer Key & Secret
     226        // Generate Consumer Key & Secret
    225227        $consumer_key = 'ck_' . wc_rand_hash();
    226228        $consumer_secret = 'cs_' . wc_rand_hash();
    227229
    228         // Erstelle API Key in WooCommerce Datenbank
     230        // Create API Key in WooCommerce Database
    229231        $key_id = $wpdb->insert(
    230232            $wpdb->prefix . 'woocommerce_api_keys',
     
    243245            return new WP_Error(
    244246                'key_creation_failed',
    245                 'Fehler beim Erstellen der WooCommerce API Keys',
     247                __('Error creating WooCommerce API Keys', 'artidomo-print-on-demand'),
    246248                array('status' => 500)
    247249            );
     
    259261     */
    260262    public function handle_disconnect_request($request) {
    261         // Lösche WooCommerce API Keys
     263        // Delete WooCommerce API Keys
    262264        $api_key_id = get_option('artidomo_api_key_id');
    263265        if ($api_key_id) {
     
    270272        }
    271273
    272         // Lösche alle gespeicherten Credentials
     274        // Delete all saved credentials
    273275        delete_option('artidomo_connected');
    274276        delete_option('artidomo_shop_id');
     
    279281        delete_option('artidomo_connected_at');
    280282
    281         // Deregistriere Webhooks
     283        // Unregister Webhooks
    282284        $this->unregister_webhooks();
    283285
    284286        return rest_ensure_response(array(
    285287            'success' => true,
    286             'message' => 'Verbindung getrennt und API Keys gelöscht',
     288            'message' => __('Connection disconnected and API Keys deleted', 'artidomo-print-on-demand'),
    287289        ));
    288290    }
    289291
    290292    /**
    291      * Admin Post Handler für Disconnect (von Form aufgerufen)
     293     * Admin Post Handler for Disconnect (called from Form)
    292294     */
    293295    public function admin_post_disconnect() {
    294         // Nonce Prüfung
     296        // Nonce Check
    295297        if (!isset($_POST['_wpnonce']) || !wp_verify_nonce($_POST['_wpnonce'], 'artidomo_disconnect')) {
    296             wp_die('Sicherheitsprüfung fehlgeschlagen');
    297         }
    298 
    299         // Prüfe Berechtigung
     298            wp_die(esc_html__('Security check failed', 'artidomo-print-on-demand'));
     299        }
     300
     301        // Check Permission
    300302        if (!current_user_can('manage_woocommerce')) {
    301             wp_die('Keine Berechtigung');
    302         }
    303 
    304         // Führe Disconnect-Logik aus
     303            wp_die(esc_html__('No permission', 'artidomo-print-on-demand'));
     304        }
     305
     306        // Execute Disconnect Logic
    305307        $api_key_id = get_option('artidomo_api_key_id');
    306308        if ($api_key_id) {
     
    313315        }
    314316
    315         // Lösche alle gespeicherten Credentials
     317        // Delete all saved credentials
    316318        delete_option('artidomo_connected');
    317319        delete_option('artidomo_shop_id');
     
    322324        delete_option('artidomo_connected_at');
    323325
    324         // Deregistriere Webhooks
     326        // Unregister Webhooks
    325327        $this->unregister_webhooks();
    326328
    327         // Redirect zurück zur Connection Page mit Erfolgs-Meldung
     329        // Redirect back to Connection Page with success message
    328330        wp_redirect(add_query_arg(
    329331            array('page' => 'artidomo-connection', 'disconnected' => '1'),
     
    350352
    351353    /**
    352      * Registriere WooCommerce Webhooks
     354     * Register WooCommerce Webhooks
    353355     */
    354356    private function register_webhooks($webhook_secret) {
    355         // Prüfe ob WooCommerce aktiv ist
     357        // Check if WooCommerce is active
    356358        if (!function_exists('wc_get_webhook')) {
    357             return new WP_Error('woocommerce_missing', 'WooCommerce nicht gefunden');
     359            return new WP_Error('woocommerce_missing', __('WooCommerce not found', 'artidomo-print-on-demand'));
    358360        }
    359361
    360362        $webhook_url = ARTIDOMO_API_URL . '/webhooks/woocommerce/order-updated';
    361363
    362         // Erstelle Order Updated Webhook
     364        // Create Order Updated Webhook
    363365        $webhook = new WC_Webhook();
    364366        $webhook->set_name('artidomo Order Updated');
     
    375377
    376378    /**
    377      * Deregistriere WooCommerce Webhooks
     379     * Unregister WooCommerce Webhooks
    378380     */
    379381    private function unregister_webhooks() {
     
    391393
    392394    /**
    393      * Füge Connection Page zum Admin Menu hinzu
     395     * Add Connection Page to Admin Menu
    394396     */
    395397    public function add_connection_page() {
    396398        add_submenu_page(
    397399            'woocommerce',
    398             'artidomo Verbindung',
     400            __('artidomo Connection', 'artidomo-print-on-demand'),
    399401            'artidomo',
    400402            'manage_woocommerce',
     
    414416        // Format connected_at for display
    415417        if ($connected_at) {
    416             $connected_at_display = date('d.m.Y H:i', strtotime($connected_at));
     418            $connected_at_display = date_i18n(get_option('date_format') . ' ' . get_option('time_format'), strtotime($connected_at));
    417419        } else {
    418             $connected_at_display = 'Unbekannt';
     420            $connected_at_display = __('Unknown', 'artidomo-print-on-demand');
    419421        }
    420422
     
    437439            ?>
    438440            <div class="notice notice-success is-dismissible">
    439                 <p><strong>✅ Update-Prüfung durchgeführt!</strong></p>
    440                 <p>WordPress wurde über verfügbare Updates informiert. Gehe zu <a href="<?php echo admin_url('plugins.php'); ?>">Plugins</a> um Updates zu installieren.</p>
     441                <p><strong>✅ <?php esc_html_e('Update check completed!', 'artidomo-print-on-demand'); ?></strong></p>
     442                <p><?php
     443                    /* translators: %s: URL to plugins page */
     444                    printf(
     445                        esc_html__('WordPress has been notified about available updates. Go to %s to install updates.', 'artidomo-print-on-demand'),
     446                        '<a href="' . esc_url(admin_url('plugins.php')) . '">' . esc_html__('Plugins', 'artidomo-print-on-demand') . '</a>'
     447                    );
     448                ?></p>
    441449            </div>
    442450            <?php
     
    447455            ?>
    448456            <div class="notice notice-success is-dismissible">
    449                 <p><strong>✅ Verbindung erfolgreich getrennt!</strong></p>
    450                 <p>API Keys wurden gelöscht und Webhooks deregistriert.</p>
     457                <p><strong>✅ <?php esc_html_e('Connection successfully disconnected!', 'artidomo-print-on-demand'); ?></strong></p>
     458                <p><?php esc_html_e('API Keys have been deleted and Webhooks unregistered.', 'artidomo-print-on-demand'); ?></p>
    451459            </div>
    452460            <?php
     
    459467            ?>
    460468            <div class="notice notice-success is-dismissible">
    461                 <p><strong>✅ Import erfolgreich!</strong></p>
    462                 <p><?php echo $imported; ?> Produkte importiert.
    463                    <?php if ($errors > 0): ?>
    464                        (<?php echo $errors; ?> Fehler)
    465                    <?php endif; ?>
    466                 </p>
     469                <p><strong>✅ <?php esc_html_e('Import successful!', 'artidomo-print-on-demand'); ?></strong></p>
     470                <p><?php
     471                    /* translators: %d: number of products imported */
     472                    printf(esc_html__('%d products imported.', 'artidomo-print-on-demand'), $imported);
     473                    if ($errors > 0) {
     474                        /* translators: %d: number of errors */
     475                        printf(' (' . esc_html__('%d errors', 'artidomo-print-on-demand') . ')', $errors);
     476                    }
     477                ?></p>
    467478            </div>
    468479            <?php
     
    524535                <div style="display: flex; align-items: center; gap: 16px;">
    525536                    <img src="https://portal.artidomo.eu/artidomo400px.png" alt="artidomo Logo" style="height: 48px;">
    526                     <h1 style="margin: 0;">Fulfillment Verbindung</h1>
     537                    <h1 style="margin: 0;"><?php esc_html_e('Fulfillment Connection', 'artidomo-print-on-demand'); ?></h1>
    527538                </div>
    528                 <a href="<?php echo add_query_arg('force_update_check', '1'); ?>" class="button button-secondary">
    529                     🔄 Nach Plugin-Updates suchen
     539                <a href="<?php echo esc_url(add_query_arg('force_update_check', '1')); ?>" class="button button-secondary">
     540                    🔄 <?php esc_html_e('Check for Plugin Updates', 'artidomo-print-on-demand'); ?>
    530541                </a>
    531542            </div>
     
    533544            <div class="artidomo-grid">
    534545            <?php if (!$is_connected): ?>
    535                 <!-- Connection Status Card (nicht verbunden) -->
     546                <!-- Connection Status Card (not connected) -->
    536547                <div class="artidomo-card">
    537                     <h3>&#x1F517; Verbindungsstatus</h3>
     548                    <h3>&#x1F517; <?php esc_html_e('Connection Status', 'artidomo-print-on-demand'); ?></h3>
    538549                    <div class="artidomo-card-content">
    539550                        <div style="text-align: center; padding: 20px 0;">
    540551                            <div style="font-size: 48px; margin-bottom: 16px;">&#x1F50C;</div>
    541                             <span class="artidomo-badge badge-info" style="font-size: 14px; padding: 8px 16px;">Noch nicht verbunden</span>
     552                            <span class="artidomo-badge badge-info" style="font-size: 14px; padding: 8px 16px;"><?php esc_html_e('Not yet connected', 'artidomo-print-on-demand'); ?></span>
    542553                            <p style="margin-top: 16px; color: #666; font-size: 14px;">
    543                                 Um deinen WooCommerce Shop mit artidomo zu verbinden, gehe zu deinem artidomo Portal und wähle "Shop hinzufügen".
     554                                <?php esc_html_e('To connect your WooCommerce shop with artidomo, go to your artidomo Portal and select "Add Shop".', 'artidomo-print-on-demand'); ?>
    544555                            </p>
    545556                        </div>
     
    547558                </div>
    548559
    549                 <!-- Datenschutz Card -->
     560                <!-- Privacy Card -->
    550561                <div class="artidomo-card" style="border-left: 4px solid #ff9800;">
    551                     <h3>🔐 Datenschutz-Hinweis</h3>
     562                    <h3>🔐 <?php esc_html_e('Privacy Notice', 'artidomo-print-on-demand'); ?></h3>
    552563                    <div class="artidomo-card-content">
    553                         <p><strong>Durch die Verbindung mit artidomo werden folgende Daten an portal.artidomo.eu übermittelt:</strong></p>
     564                        <p><strong><?php esc_html_e('By connecting to artidomo, the following data will be transmitted to portal.artidomo.eu:', 'artidomo-print-on-demand'); ?></strong></p>
    554565                        <ul style="list-style: disc; margin-left: 20px; margin-top: 12px;">
    555                             <li>WooCommerce REST API Zugangsdaten (Consumer Key & Consumer Secret)</li>
    556                             <li>Shop-URL und Bestelldaten</li>
    557                             <li>Produktinformationen und Personalisierungsdaten</li>
     566                            <li><?php esc_html_e('WooCommerce REST API credentials (Consumer Key & Consumer Secret)', 'artidomo-print-on-demand'); ?></li>
     567                            <li><?php esc_html_e('Shop URL and order data', 'artidomo-print-on-demand'); ?></li>
     568                            <li><?php esc_html_e('Product information and personalization data', 'artidomo-print-on-demand'); ?></li>
    558569                        </ul>
    559                         <p style="margin-top: 16px;"><strong>Diese Verbindung ist nur möglich wenn:</strong></p>
     570                        <p style="margin-top: 16px;"><strong><?php esc_html_e('This connection is only possible if:', 'artidomo-print-on-demand'); ?></strong></p>
    560571                        <ul style="list-style: disc; margin-left: 20px; margin-top: 12px;">
    561                             <li>Ein aktiver Vertrag mit artidomo besteht</li>
    562                             <li>Die Auftragsverarbeitungsvereinbarung (ADV) unterzeichnet wurde</li>
     572                            <li><?php esc_html_e('An active contract with artidomo exists', 'artidomo-print-on-demand'); ?></li>
     573                            <li><?php esc_html_e('The Data Processing Agreement (DPA) has been signed', 'artidomo-print-on-demand'); ?></li>
    563574                        </ul>
    564575                        <p style="margin-top: auto; padding: 12px; background: #fff3cd; border-radius: 4px; font-size: 13px;">
    565                             Die Daten werden ausschließlich zur Abwicklung Ihrer Druckaufträge verwendet.<br>
    566                             Bei Fragen kontaktieren Sie bitte: <a href="mailto:[email protected]">[email protected]</a>
     576                            <?php esc_html_e('The data is used exclusively for processing your print orders.', 'artidomo-print-on-demand'); ?><br>
     577                            <?php
     578                            /* translators: %s: support email address */
     579                            printf(esc_html__('For questions, please contact: %s', 'artidomo-print-on-demand'), '<a href="mailto:[email protected]">[email protected]</a>');
     580                            ?>
    567581                        </p>
    568582                    </div>
     
    571585                <!-- Token Input Card -->
    572586                <div class="artidomo-card" style="border-left: 4px solid #3c8735;">
    573                     <h3>🔑 Manuelle Verbindung via Token</h3>
     587                    <h3>🔑 <?php esc_html_e('Manual Connection via Token', 'artidomo-print-on-demand'); ?></h3>
    574588                    <div class="artidomo-card-content">
    575                         <p style="margin-bottom: 16px;">Falls du einen Connection Token hast, kannst du ihn hier eingeben:</p>
     589                        <p style="margin-bottom: 16px;"><?php esc_html_e('If you have a connection token, you can enter it here:', 'artidomo-print-on-demand'); ?></p>
    576590
    577591                        <?php if ($portal_token): ?>
    578592                            <div style="background: #d4edda; padding: 12px; border-radius: 4px; margin-bottom: 16px;">
    579                                 <strong>✓ Token automatisch aus dem Portal übernommen</strong>
     593                                <strong>✓ <?php esc_html_e('Token automatically received from Portal', 'artidomo-print-on-demand'); ?></strong>
    580594                            </div>
    581595                        <?php endif; ?>
     
    585599                            <input type="text"
    586600                                   id="artidomo-token"
    587                                    placeholder="Token hier einfügen"
     601                                   placeholder="<?php esc_attr_e('Paste token here', 'artidomo-print-on-demand'); ?>"
    588602                                   value="<?php echo esc_attr($portal_token); ?>"
    589603                                   style="width: 100%; padding: 10px; font-family: monospace; border: 1px solid #ddd; border-radius: 4px; margin-bottom: 12px;">
    590604                            <button type="submit" class="button button-primary" style="width: 100%; padding: 10px; font-size: 14px;">
    591                                 🔗 Verbinden
     605                                🔗 <?php esc_html_e('Connect', 'artidomo-print-on-demand'); ?>
    592606                            </button>
    593607                        </form>
     
    597611                </div>
    598612
    599                 <!-- Germanized und German Market Erkennung -->
     613                <!-- German Market / Germanized Detection -->
    600614                <div class="artidomo-card">
    601                     <h3>🔌 Germanized und German Market Erkennung</h3>
     615                    <h3>🔌 <?php esc_html_e('German Market & Germanized Detection', 'artidomo-print-on-demand'); ?></h3>
    602616                    <div class="artidomo-card-content">
    603617                        <?php if (!empty($detected_plugins)): ?>
     
    605619                                <div style="display: flex; align-items: center; gap: 8px; margin-bottom: 12px;">
    606620                                    <span class="artidomo-badge badge-success">✓ <?php echo esc_html($plugin['name']); ?></span>
    607                                     <span style="color: #666; font-size: 12px;">(Version: <?php echo esc_html($plugin['version']); ?>)</span>
     621                                    <span style="color: #666; font-size: 12px;">(<?php
     622                                        /* translators: %s: plugin version number */
     623                                        printf(esc_html__('Version: %s', 'artidomo-print-on-demand'), esc_html($plugin['version']));
     624                                    ?>)</span>
    608625                                </div>
    609626                            <?php endforeach; ?>
     
    611628                            <div style="margin-top: 16px; padding: 12px; background: #fff3cd; border-left: 4px solid #ffc107; border-radius: 4px;">
    612629                                <p style="margin: 0; font-size: 13px; color: #856404;">
    613                                     <strong>⚠️ Wichtig:</strong> <?php echo esc_html($detected_plugins[0]['name']); ?> ändert den Status "Bezahlt" anders als Standard-WooCommerce.
     630                                    <strong>⚠️ <?php esc_html_e('Important:', 'artidomo-print-on-demand'); ?></strong> <?php echo esc_html($detected_plugins[0]['name']); ?> <?php esc_html_e('changes the "Paid" status differently than standard WooCommerce.', 'artidomo-print-on-demand'); ?>
    614631                                </p>
    615632                                <p style="margin: 8px 0 0 0; font-size: 12px; color: #856404;">
    616                                     <strong>Nur Bestellungen die als "Bezahlt" markiert sind werden zu artidomo übertragen.</strong> Dies gewährleistet, dass nur tatsächlich bezahlte Bestellungen produziert werden.
     633                                    <strong><?php esc_html_e('Only orders marked as "Paid" will be transferred to artidomo.', 'artidomo-print-on-demand'); ?></strong> <?php esc_html_e('This ensures that only actually paid orders are produced.', 'artidomo-print-on-demand'); ?>
    617634                                </p>
    618635                            </div>
    619636
    620637                            <p style="margin-top: 12px; color: #666; font-size: 13px;">
    621                                 <em>Diese Informationen werden automatisch an das artidomo Backend übermittelt für optimale Bestellverarbeitung.</em>
     638                                <em><?php esc_html_e('This information is automatically sent to the artidomo backend for optimal order processing.', 'artidomo-print-on-demand'); ?></em>
    622639                            </p>
    623640                        <?php else: ?>
    624                             <p style="color: #666; font-size: 13px;">Keine German Market oder Germanized Plugins erkannt.</p>
     641                            <p style="color: #666; font-size: 13px;"><?php esc_html_e('No German Market or Germanized plugins detected.', 'artidomo-print-on-demand'); ?></p>
    625642                            <div style="margin-top: 12px; padding: 12px; background: #d1ecf1; border-left: 4px solid #0c5460; border-radius: 4px;">
    626643                                <p style="margin: 0; font-size: 12px; color: #0c5460;">
    627                                     <strong>Standard-WooCommerce:</strong> Nur Bestellungen die als "Bezahlt" markiert sind werden zu artidomo übertragen.
     644                                    <strong><?php esc_html_e('Standard WooCommerce:', 'artidomo-print-on-demand'); ?></strong> <?php esc_html_e('Only orders marked as "Paid" will be transferred to artidomo.', 'artidomo-print-on-demand'); ?>
    628645                                </p>
    629646                            </div>
     
    632649                </div>
    633650            <?php else: ?>
    634                 <!-- Zuordnungs-Statistik Card -->
     651                <!-- Product Mapping Statistics Card -->
    635652                <?php
    636653                $stats = Artidomo_CSV_Handler::get_statistics();
    637654                ?>
    638655                <div class="artidomo-card" style="border-left: 4px solid #3c8735;">
    639                     <h3>📊 Produktzuordnungs-Statistik</h3>
     656                    <h3>📊 <?php esc_html_e('Product Mapping Statistics', 'artidomo-print-on-demand'); ?></h3>
    640657                    <div class="artidomo-card-content">
    641658                        <div style="display: flex; gap: 24px; justify-content: space-around; padding: 20px 0;">
    642659                            <div style="text-align: center;">
    643                                 <div style="font-size: 36px; font-weight: 700; color: #3c8735;"><?php echo $stats['total_mapped']; ?></div>
    644                                 <div style="color: #666; font-size: 13px; margin-top: 8px;">Produkte mit SKU</div>
     660                                <div style="font-size: 36px; font-weight: 700; color: #3c8735;"><?php echo esc_html($stats['total_mapped']); ?></div>
     661                                <div style="color: #666; font-size: 13px; margin-top: 8px;"><?php esc_html_e('Products with SKU', 'artidomo-print-on-demand'); ?></div>
    645662                            </div>
    646663                            <div style="text-align: center;">
    647                                 <div style="font-size: 36px; font-weight: 700; color: #3c8735;"><?php echo $stats['with_printfile']; ?></div>
    648                                 <div style="color: #666; font-size: 13px; margin-top: 8px;">mit Druckdatei</div>
     664                                <div style="font-size: 36px; font-weight: 700; color: #3c8735;"><?php echo esc_html($stats['with_printfile']); ?></div>
     665                                <div style="color: #666; font-size: 13px; margin-top: 8px;"><?php esc_html_e('with print file', 'artidomo-print-on-demand'); ?></div>
    649666                            </div>
    650667                        </div>
    651668                        <div style="margin-top: auto; text-align: center;">
    652                             <a href="<?php echo admin_url('admin.php?page=artidomo-all-mappings'); ?>" class="button button-primary" style="width: 100%;">
    653                                 Alle Zuordnungen anzeigen
     669                            <a href="<?php echo esc_url(admin_url('admin.php?page=artidomo-all-mappings')); ?>" class="button button-primary" style="width: 100%;">
     670                                <?php esc_html_e('Show all mappings', 'artidomo-print-on-demand'); ?>
    654671                            </a>
    655672                        </div>
     
    657674                </div>
    658675
    659                 <!-- Connection Status Card (verbunden) -->
     676                <!-- Connection Status Card (connected) -->
    660677                <div class="artidomo-card">
    661                     <h3>&#x1F517; Verbindungsstatus</h3>
     678                    <h3>&#x1F517; <?php esc_html_e('Connection Status', 'artidomo-print-on-demand'); ?></h3>
    662679                    <div class="artidomo-card-content">
    663680                        <div style="text-align: center; padding: 20px 0;">
    664681                            <div style="font-size: 48px; margin-bottom: 16px;">&#x2705;</div>
    665                             <span class="artidomo-badge badge-success" style="font-size: 14px; padding: 8px 16px;">Verbunden</span>
     682                            <span class="artidomo-badge badge-success" style="font-size: 14px; padding: 8px 16px;"><?php esc_html_e('Connected', 'artidomo-print-on-demand'); ?></span>
    666683                            <p style="margin-top: 16px; color: #666;">
    667                                 Webhooks aktiv und<br>
    668                                 API Keys konfiguriert
     684                                <?php esc_html_e('Webhooks active and', 'artidomo-print-on-demand'); ?><br>
     685                                <?php esc_html_e('API Keys configured', 'artidomo-print-on-demand'); ?>
    669686                            </p>
    670687                            <p style="color: #888; font-size: 12px; margin-top: 8px;">
    671                                 Verbunden seit: <?php echo esc_html($connected_at_display); ?>
     688                                <?php
     689                                /* translators: %s: connection date */
     690                                printf(esc_html__('Connected since: %s', 'artidomo-print-on-demand'), esc_html($connected_at_display));
     691                                ?>
    672692                            </p>
    673693                        </div>
    674                         <form method="post" action="<?php echo admin_url('admin-post.php'); ?>" style="text-align: center; margin-top: auto;">
     694                        <form method="post" action="<?php echo esc_url(admin_url('admin-post.php')); ?>" style="text-align: center; margin-top: auto;">
    675695                            <?php wp_nonce_field('artidomo_disconnect'); ?>
    676696                            <input type="hidden" name="action" value="artidomo_disconnect">
    677697                            <button type="submit" class="button button-secondary" style="width: 100%;">
    678                                 Verbindung trennen
     698                                <?php esc_html_e('Disconnect', 'artidomo-print-on-demand'); ?>
    679699                            </button>
    680700                        </form>
     
    682702                </div>
    683703
    684                 <!-- Germanized und German Market Erkennung -->
     704                <!-- German Market / Germanized Detection (connected) -->
    685705                <div class="artidomo-card">
    686                     <h3>🔌 Germanized und German Market Erkennung</h3>
     706                    <h3>🔌 <?php esc_html_e('German Market & Germanized Detection', 'artidomo-print-on-demand'); ?></h3>
    687707                    <div class="artidomo-card-content">
    688708                        <?php if (!empty($detected_plugins)): ?>
     
    690710                                <div style="display: flex; align-items: center; gap: 8px; margin-bottom: 12px;">
    691711                                    <span class="artidomo-badge badge-success">✓ <?php echo esc_html($plugin['name']); ?></span>
    692                                     <span style="color: #666; font-size: 12px;">(Version: <?php echo esc_html($plugin['version']); ?>)</span>
     712                                    <span style="color: #666; font-size: 12px;">(<?php
     713                                        /* translators: %s: plugin version number */
     714                                        printf(esc_html__('Version: %s', 'artidomo-print-on-demand'), esc_html($plugin['version']));
     715                                    ?>)</span>
    693716                                </div>
    694717                            <?php endforeach; ?>
     
    696719                            <div style="margin-top: 16px; padding: 12px; background: #fff3cd; border-left: 4px solid #ffc107; border-radius: 4px;">
    697720                                <p style="margin: 0; font-size: 13px; color: #856404;">
    698                                     <strong>⚠️ Wichtig:</strong> <?php echo esc_html($detected_plugins[0]['name']); ?> ändert den Status "Bezahlt" anders als Standard-WooCommerce.
     721                                    <strong>⚠️ <?php esc_html_e('Important:', 'artidomo-print-on-demand'); ?></strong> <?php echo esc_html($detected_plugins[0]['name']); ?> <?php esc_html_e('changes the "Paid" status differently than standard WooCommerce.', 'artidomo-print-on-demand'); ?>
    699722                                </p>
    700723                                <p style="margin: 8px 0 0 0; font-size: 12px; color: #856404;">
    701                                     <strong>Nur Bestellungen die als "Bezahlt" markiert sind werden zu artidomo übertragen.</strong> Dies gewährleistet, dass nur tatsächlich bezahlte Bestellungen produziert werden.
     724                                    <strong><?php esc_html_e('Only orders marked as "Paid" will be transferred to artidomo.', 'artidomo-print-on-demand'); ?></strong> <?php esc_html_e('This ensures that only actually paid orders are produced.', 'artidomo-print-on-demand'); ?>
    702725                                </p>
    703726                            </div>
    704727
    705728                            <p style="margin-top: 12px; color: #666; font-size: 13px;">
    706                                 <em>Diese Informationen werden automatisch an das artidomo Backend übermittelt für optimale Bestellverarbeitung.</em>
     729                                <em><?php esc_html_e('This information is automatically sent to the artidomo backend for optimal order processing.', 'artidomo-print-on-demand'); ?></em>
    707730                            </p>
    708731                        <?php else: ?>
    709                             <p style="color: #666; font-size: 13px;">Keine German Market oder Germanized Plugins erkannt.</p>
     732                            <p style="color: #666; font-size: 13px;"><?php esc_html_e('No German Market or Germanized plugins detected.', 'artidomo-print-on-demand'); ?></p>
    710733                            <div style="margin-top: 12px; padding: 12px; background: #d1ecf1; border-left: 4px solid #0c5460; border-radius: 4px;">
    711734                                <p style="margin: 0; font-size: 12px; color: #0c5460;">
    712                                     <strong>Standard-WooCommerce:</strong> Nur Bestellungen die als "Bezahlt" markiert sind werden zu artidomo übertragen.
     735                                    <strong><?php esc_html_e('Standard WooCommerce:', 'artidomo-print-on-demand'); ?></strong> <?php esc_html_e('Only orders marked as "Paid" will be transferred to artidomo.', 'artidomo-print-on-demand'); ?>
    713736                                </p>
    714737                            </div>
     
    719742                <!-- CSV Export Box -->
    720743                <div class="artidomo-card">
    721                     <h3>📤 CSV Export</h3>
     744                    <h3>📤 <?php esc_html_e('CSV Export', 'artidomo-print-on-demand'); ?></h3>
    722745                    <div class="artidomo-card-content">
    723746                        <p style="color: #666; font-size: 13px; margin-bottom: 16px;">
    724                             Exportiere alle Produktzuordnungen als CSV-Datei mit artidomo SKU, Druckdateien und Personalisierungs-Einstellungen.
     747                            <?php esc_html_e('Export all product mappings as CSV file with artidomo SKU, print files, and personalization settings.', 'artidomo-print-on-demand'); ?>
    725748                        </p>
    726749
    727                         <form method="post" action="<?php echo admin_url('admin-post.php'); ?>" style="margin-top: auto;">
     750                        <form method="post" action="<?php echo esc_url(admin_url('admin-post.php')); ?>" style="margin-top: auto;">
    728751                            <?php wp_nonce_field('artidomo_export_csv'); ?>
    729752                            <input type="hidden" name="action" value="artidomo_export_csv">
     
    732755                                    style="width: 100%; padding: 10px; background: #28a745; border-color: #28a745;"
    733756                                    <?php if ($stats['total_mapped'] === 0) echo 'disabled'; ?>>
    734                                 📥 CSV exportieren (<?php echo $stats['total_mapped']; ?> Produkte)
     757                                📥 <?php
     758                                /* translators: %d: number of products */
     759                                printf(esc_html__('Export CSV (%d products)', 'artidomo-print-on-demand'), $stats['total_mapped']);
     760                                ?>
    735761                            </button>
    736762                        </form>
     
    740766                <!-- CSV Import Box -->
    741767                <div class="artidomo-card">
    742                     <h3>📥 CSV Import</h3>
     768                    <h3>📥 <?php esc_html_e('CSV Import', 'artidomo-print-on-demand'); ?></h3>
    743769                    <div class="artidomo-card-content">
    744770                        <p style="color: #666; font-size: 13px; margin-bottom: 12px;">
    745                             Importiere Produktzuordnungen aus einer CSV-Datei.
     771                            <?php esc_html_e('Import product mappings from a CSV file.', 'artidomo-print-on-demand'); ?>
    746772                        </p>
    747773
    748774                        <details style="margin-bottom: 12px;">
    749775                            <summary style="cursor: pointer; color: #2271b1; font-size: 12px; font-weight: 600;">
    750                                 ℹ️ CSV Format-Anforderungen
     776                                ℹ️ <?php esc_html_e('CSV Format Requirements', 'artidomo-print-on-demand'); ?>
    751777                            </summary>
    752778                            <ul style="list-style: disc; margin: 8px 0 0 20px; font-size: 11px; color: #666;">
    753                                 <li>Semikolon-getrennt (;)</li>
    754                                 <li>UTF-8 Kodierung</li>
    755                                 <li>Header-Zeile erforderlich</li>
    756                                 <li>Spalten: Produkt ID, Varianten ID, Produktname, Variantenname, WooCommerce SKU, artidomo SKU, Druckdatei, Dateiquelle</li>
     779                                <li><?php esc_html_e('Semicolon-separated (;)', 'artidomo-print-on-demand'); ?></li>
     780                                <li><?php esc_html_e('UTF-8 encoding', 'artidomo-print-on-demand'); ?></li>
     781                                <li><?php esc_html_e('Header row required', 'artidomo-print-on-demand'); ?></li>
     782                                <li><?php esc_html_e('Columns: Product ID, Variation ID, Product Name, Variation Name, WooCommerce SKU, artidomo SKU, Print File, File Source', 'artidomo-print-on-demand'); ?></li>
    757783                            </ul>
    758784                        </details>
    759785
    760786                        <form method="post"
    761                               action="<?php echo admin_url('admin-post.php'); ?>"
     787                              action="<?php echo esc_url(admin_url('admin-post.php')); ?>"
    762788                              enctype="multipart/form-data"
    763789                              style="margin-top: auto;">
     
    766792                            <input type="file" name="csv_file" accept=".csv" required style="width: 100%; margin-bottom: 8px;">
    767793                            <button type="submit" class="button button-primary" style="width: 100%; padding: 10px; background: #2271b1; border-color: #2271b1;">
    768                                 📤 CSV importieren
     794                                📤 <?php esc_html_e('Import CSV', 'artidomo-print-on-demand'); ?>
    769795                            </button>
    770796                        </form>
    771797
    772798                        <div style="margin-top: 12px; padding: 12px; background: #fff3cd; border-left: 4px solid #ffc107; border-radius: 4px; font-size: 12px;">
    773                             <strong>💡 Tipp:</strong> Exportiere zuerst eine CSV um das Format zu sehen.
     799                            <strong>💡 <?php esc_html_e('Tip:', 'artidomo-print-on-demand'); ?></strong> <?php esc_html_e('Export a CSV first to see the format.', 'artidomo-print-on-demand'); ?>
    774800                        </div>
    775801                    </div>
     
    783809            <?php endif; ?>
    784810
    785             <!-- Impressum -->
     811            <!-- Imprint -->
    786812            <div style="margin-top: 40px; padding: 24px; background: #f9f9f9; border-top: 3px solid #3c8735; border-radius: 8px;">
    787                 <h3 style="margin-top: 0; color: #3c8735;">📄 Impressum</h3>
     813                <h3 style="margin-top: 0; color: #3c8735;">📄 <?php esc_html_e('Imprint', 'artidomo-print-on-demand'); ?></h3>
    788814                <div style="display: grid; grid-template-columns: repeat(auto-fit, minmax(250px, 1fr)); gap: 24px;">
    789815                    <div>
    790816                        <p style="margin: 0 0 8px 0;"><strong>artidomo</strong></p>
    791                         <p style="margin: 0; color: #666;">Inhaberin: Marina Scheubly</p>
     817                        <p style="margin: 0; color: #666;"><?php esc_html_e('Owner: Marina Scheubly', 'artidomo-print-on-demand'); ?></p>
    792818                        <p style="margin: 4px 0 0 0; color: #666;">
    793819                            Wittener Str. 75<br>
    794820                            44789 Bochum<br>
    795                             Deutschland
     821                            <?php esc_html_e('Germany', 'artidomo-print-on-demand'); ?>
    796822                        </p>
    797823                    </div>
    798824                    <div>
    799                         <p style="margin: 0 0 8px 0;"><strong>Kontakt</strong></p>
     825                        <p style="margin: 0 0 8px 0;"><strong><?php esc_html_e('Contact', 'artidomo-print-on-demand'); ?></strong></p>
    800826                        <p style="margin: 0; color: #666;">
    801                             Tel: +49-(0)234-52009829<br>
    802                             E-Mail: <a href="mailto:[email protected]">[email protected]</a><br>
    803                             Web: <a href="https://www.artidomo.eu" target="_blank">www.artidomo.eu</a>
     827                            <?php esc_html_e('Phone:', 'artidomo-print-on-demand'); ?> +49-(0)234-52009829<br>
     828                            <?php esc_html_e('Email:', 'artidomo-print-on-demand'); ?> <a href="mailto:[email protected]">[email protected]</a><br>
     829                            <?php esc_html_e('Web:', 'artidomo-print-on-demand'); ?> <a href="https://www.artidomo.eu" target="_blank">www.artidomo.eu</a>
    804830                        </p>
    805831                    </div>
    806832                    <div>
    807                         <p style="margin: 0 0 8px 0;"><strong>Rechtliches</strong></p>
     833                        <p style="margin: 0 0 8px 0;"><strong><?php esc_html_e('Legal', 'artidomo-print-on-demand'); ?></strong></p>
    808834                        <p style="margin: 0; color: #666;">
    809                             USt-ID: DE304587715
     835                            <?php esc_html_e('VAT ID:', 'artidomo-print-on-demand'); ?> DE304587715
    810836                        </p>
    811837                    </div>
    812838                </div>
    813839                <p style="margin-top: 16px; font-size: 12px; color: #888; border-top: 1px solid #ddd; padding-top: 16px;">
    814                     artidomo ist eine eingetragene Wort- und Bildmarke.
     840                    <?php esc_html_e('artidomo is a registered word and image mark.', 'artidomo-print-on-demand'); ?>
    815841                </p>
    816842            </div>
     
    819845        <script>
    820846        jQuery(document).ready(function($) {
    821             // Auto-submit wenn Token aus URL kommt (nach 2 Sekunden)
     847            // Auto-submit when Token comes from URL (after 2 seconds)
    822848            <?php if ($portal_token): ?>
    823849            setTimeout(function() {
    824                 if (confirm('Token aus Portal erkannt. Jetzt verbinden?')) {
     850                if (confirm('<?php echo esc_js(__('Token from Portal detected. Connect now?', 'artidomo-print-on-demand')); ?>')) {
    825851                    $('#artidomo-manual-connect-form').submit();
    826852                }
     
    833859                var token = $('#artidomo-token').val();
    834860                if (!token) {
    835                     alert('Bitte Token eingeben');
     861                    alert('<?php echo esc_js(__('Please enter a token', 'artidomo-print-on-demand')); ?>');
    836862                    return;
    837863                }
    838864
    839                 $('#artidomo-connect-result').html('<p style="text-align: center; padding: 12px; background: #fff3cd; border-radius: 4px;">🔄 Verbinde mit artidomo...</p>');
     865                $('#artidomo-connect-result').html('<p style="text-align: center; padding: 12px; background: #fff3cd; border-radius: 4px;">🔄 <?php echo esc_js(__('Connecting to artidomo...', 'artidomo-print-on-demand')); ?></p>');
    840866
    841867                $.ajax({
    842                     url: '<?php echo rest_url('artidomo/v1/connect'); ?>',
     868                    url: '<?php echo esc_url(rest_url('artidomo/v1/connect')); ?>',
    843869                    method: 'POST',
    844870                    data: JSON.stringify({ token: token }),
     
    853879                    },
    854880                    error: function(xhr) {
    855                         var error = xhr.responseJSON?.message || 'Verbindung fehlgeschlagen';
     881                        var error = xhr.responseJSON?.message || '<?php echo esc_js(__('Connection failed', 'artidomo-print-on-demand')); ?>';
    856882                        $('#artidomo-connect-result').html(
    857883                            '<div style="background: #f8d7da; padding: 12px; border-radius: 4px; text-align: center;"><strong>❌ ' + error + '</strong></div>'
     
    872898        global $wpdb;
    873899
    874         // Hole alle Produkte mit artidomo SKU (maximal 5)
     900        // Get all products with artidomo SKU (max 5)
    875901        $products = $wpdb->get_results(
    876902            "SELECT DISTINCT pm.post_id, pm.meta_value as artidomo_sku
     
    889915            <div class="artidomo-card" style="margin-top: 24px; text-align: center; padding: 40px 24px;">
    890916                <div style="font-size: 48px; margin-bottom: 16px; opacity: 0.5;">🏷️</div>
    891                 <h3>Produkt-Zuordnungen</h3>
     917                <h3><?php esc_html_e('Product Mappings', 'artidomo-print-on-demand'); ?></h3>
    892918                <p style="color: #666; margin-top: 16px;">
    893                     Noch keine Produkte zugeordnet. Gehe zu einem Produkt und füge eine artidomo SKU hinzu.
     919                    <?php esc_html_e('No products mapped yet. Go to a product and add an artidomo SKU.', 'artidomo-print-on-demand'); ?>
    894920                </p>
    895                 <a href="<?php echo admin_url('edit.php?post_type=product'); ?>" class="button button-primary" style="margin-top: 16px;">
    896                     Zu den Produkten
     921                <a href="<?php echo esc_url(admin_url('edit.php?post_type=product')); ?>" class="button button-primary" style="margin-top: 16px;">
     922                    <?php esc_html_e('Go to Products', 'artidomo-print-on-demand'); ?>
    897923                </a>
    898924            </div>
     
    904930        <div class="artidomo-card" style="margin-top: 24px;">
    905931            <div style="display: flex; justify-content: space-between; align-items: center; margin-bottom: 16px;">
    906                 <h3 style="margin: 0;">🏷️ Produkt-Zuordnungen</h3>
     932                <h3 style="margin: 0;">🏷️ <?php esc_html_e('Product Mappings', 'artidomo-print-on-demand'); ?></h3>
    907933                <div style="display: flex; gap: 8px;">
    908                     <a href="<?php echo admin_url('admin.php?page=artidomo-all-mappings'); ?>" class="button button-primary">
    909                         Alle Produktzuordnungen anzeigen
     934                    <a href="<?php echo esc_url(admin_url('admin.php?page=artidomo-all-mappings')); ?>" class="button button-primary">
     935                        <?php esc_html_e('Show all product mappings', 'artidomo-print-on-demand'); ?>
    910936                    </a>
    911                     <a href="<?php echo admin_url('edit.php?post_type=product'); ?>" class="button button-secondary">
    912                         zur WooCommerce Produktverwaltung
     937                    <a href="<?php echo esc_url(admin_url('edit.php?post_type=product')); ?>" class="button button-secondary">
     938                        <?php esc_html_e('Go to WooCommerce Product Management', 'artidomo-print-on-demand'); ?>
    913939                    </a>
    914940                </div>
     
    916942
    917943            <p style="color: #666; margin-bottom: 20px; font-size: 13px;">
    918                 Hier werden nur die letzten 5 Zuordnungen angezeigt. Du kannst die Zuordnung besser im Fulfillment-Portal vornehmen. Aber es geht auch in WooCommerce unter den Produkten: Bei Einzelprodukten unter dem Reiter "artidomo" und bei Varianten-Produkten direkt in der Variante selbst.
     944                <?php esc_html_e('Only the last 5 mappings are shown here. You can manage mappings better in the Fulfillment Portal. But you can also do it in WooCommerce under Products: For simple products under the "artidomo" tab and for variable products directly in the variation.', 'artidomo-print-on-demand'); ?>
    919945            </p>
    920946
     
    923949                    <thead>
    924950                        <tr style="background: #f9f9f9;">
    925                             <th style="width: 60px; padding: 12px; font-weight: 600;">ID</th>
    926                             <th style="padding: 12px; font-weight: 600;">Produktname</th>
    927                             <th style="padding: 12px; font-weight: 600;">WooCommerce SKU</th>
    928                             <th style="width: 150px; padding: 12px; font-weight: 600;">artidomo SKU</th>
    929                             <th style="width: 150px; padding: 12px; font-weight: 600;">Druckdatei</th>
    930                             <th style="width: 100px; padding: 12px; font-weight: 600;">Aktion</th>
     951                            <th style="width: 60px; padding: 12px; font-weight: 600;"><?php esc_html_e('ID', 'artidomo-print-on-demand'); ?></th>
     952                            <th style="padding: 12px; font-weight: 600;"><?php esc_html_e('Product Name', 'artidomo-print-on-demand'); ?></th>
     953                            <th style="padding: 12px; font-weight: 600;"><?php esc_html_e('WooCommerce SKU', 'artidomo-print-on-demand'); ?></th>
     954                            <th style="width: 150px; padding: 12px; font-weight: 600;"><?php esc_html_e('artidomo SKU', 'artidomo-print-on-demand'); ?></th>
     955                            <th style="width: 150px; padding: 12px; font-weight: 600;"><?php esc_html_e('Print File', 'artidomo-print-on-demand'); ?></th>
     956                            <th style="width: 100px; padding: 12px; font-weight: 600;"><?php esc_html_e('Action', 'artidomo-print-on-demand'); ?></th>
    931957                        </tr>
    932958                    </thead>
     
    940966                            $artidomo_sku = get_post_meta($product_id, '_artidomo_sku', true);
    941967                            $printfilename = get_post_meta($product_id, '_artidomo_printfilename', true);
    942                             $personalization_provider = get_post_meta($product_id, '_artidomo_personalization_provider', true);
    943968
    944969                            $is_variation = $product->get_type() === 'variation';
     
    948973                        ?>
    949974                        <tr style="border-bottom: 1px solid #eee;">
    950                             <td style="padding: 12px;"><?php echo $product_id; ?></td>
     975                            <td style="padding: 12px;"><?php echo esc_html($product_id); ?></td>
    951976                            <td style="padding: 12px;">
    952977                                <strong><?php echo esc_html($product->get_name()); ?></strong>
    953978                                <?php if ($is_variation): ?>
    954                                     <br><small style="color: #999;">↳ Variante von #<?php echo $product->get_parent_id(); ?></small>
     979                                    <br><small style="color: #999;">↳ <?php
     980                                        /* translators: %d: parent product ID */
     981                                        printf(esc_html__('Variation of #%d', 'artidomo-print-on-demand'), $product->get_parent_id());
     982                                    ?></small>
    955983                                <?php endif; ?>
    956984                            </td>
     
    959987                            <td style="padding: 12px; font-size: 12px; color: #666;"><?php echo esc_html($printfilename ?: '—'); ?></td>
    960988                            <td style="padding: 12px;">
    961                                 <a href="<?php echo $edit_url; ?>" class="button button-small" style="font-size: 11px; padding: 4px 8px;">
    962                                     ✏️ Bearbeiten
     989                                <a href="<?php echo esc_url($edit_url); ?>" class="button button-small" style="font-size: 11px; padding: 4px 8px;">
     990                                    ✏️ <?php esc_html_e('Edit', 'artidomo-print-on-demand'); ?>
    963991                                </a>
    964992                            </td>
     
    971999            <?php if (count($products) >= 5): ?>
    9721000                <p style="margin-top: 16px; text-align: center; color: #888; font-size: 12px; padding: 12px; background: #f9f9f9; border-radius: 4px;">
    973                     Zeige die letzten 5 Produkte. <a href="<?php echo admin_url('admin.php?page=artidomo-all-mappings'); ?>" style="color: #3c8735; font-weight: 600;">Alle Produktzuordnungen anzeigen →</a>
     1001                    <?php esc_html_e('Showing the last 5 products.', 'artidomo-print-on-demand'); ?> <a href="<?php echo esc_url(admin_url('admin.php?page=artidomo-all-mappings')); ?>" style="color: #3c8735; font-weight: 600;"><?php esc_html_e('Show all product mappings', 'artidomo-print-on-demand'); ?> →</a>
    9741002                </p>
    9751003            <?php endif; ?>
     
    9791007
    9801008    /**
    981      * Füge "Alle Produktzuordnungen" Submenu hinzu
     1009     * Add "All Product Mappings" Submenu
    9821010     */
    9831011    public function add_all_mappings_page() {
    9841012        add_submenu_page(
    9851013            'artidomo-connection',
    986             'artidomo Produktzuordnungen',
    987             'Zuordnungen',
     1014            __('artidomo Product Mappings', 'artidomo-print-on-demand'),
     1015            __('Mappings', 'artidomo-print-on-demand'),
    9881016            'manage_woocommerce',
    9891017            'artidomo-all-mappings',
     
    9931021
    9941022    /**
    995      * Render "Alle Produktzuordnungen" Page mit Paginierung
     1023     * Render "All Product Mappings" Page with Pagination
    9961024     */
    9971025    public function render_all_mappings_page() {
    9981026        global $wpdb;
    9991027
    1000         // Hole artidomo Preise aus der Datenbank (Backend)
     1028        // Get artidomo prices from database (Backend)
    10011029        $artidomo_prices = $this->get_artidomo_prices();
    10021030
    1003         // Paginierung
     1031        // Pagination
    10041032        $per_page = 20;
    10051033        $current_page = isset($_GET['paged']) ? max(1, intval($_GET['paged'])) : 1;
    10061034        $offset = ($current_page - 1) * $per_page;
    10071035
    1008         // Zähle alle Produkte mit artidomo SKU
     1036        // Count all products with artidomo SKU
    10091037        $total_products = $wpdb->get_var(
    10101038            "SELECT COUNT(DISTINCT pm.post_id)
     
    10161044        );
    10171045
    1018         // Hole Produkte für aktuelle Seite
     1046        // Get products for current page
    10191047        $products = $wpdb->get_results(
    10201048            $wpdb->prepare(
     
    10511079            margin-bottom: 16px;
    10521080        }
    1053         .artidomo-badge {
    1054             display: inline-block;
    1055             padding: 4px 12px;
    1056             border-radius: 12px;
    1057             font-size: 11px;
    1058             font-weight: 600;
    1059             text-transform: uppercase;
    1060             letter-spacing: 0.5px;
    1061         }
    1062         .badge-success {
    1063             background: #d4edda;
    1064             color: #155724;
    1065         }
    1066         .badge-info {
    1067             background: #d1ecf1;
    1068             color: #0c5460;
    1069         }
    1070         .badge-warning {
    1071             background: #fff3cd;
    1072             color: #856404;
    1073         }
    10741081        </style>
    10751082
     
    10781085                <div style="display: flex; align-items: center; gap: 16px;">
    10791086                    <img src="https://portal.artidomo.eu/artidomo400px.png" alt="artidomo Logo" style="height: 48px;">
    1080                     <h1 style="margin: 0;">Alle Produktzuordnungen</h1>
     1087                    <h1 style="margin: 0;"><?php esc_html_e('All Product Mappings', 'artidomo-print-on-demand'); ?></h1>
    10811088                </div>
    1082                 <a href="<?php echo admin_url('admin.php?page=artidomo-connection'); ?>" class="button button-secondary">
    1083                     ← Zurück zur Übersicht
     1089                <a href="<?php echo esc_url(admin_url('admin.php?page=artidomo-connection')); ?>" class="button button-secondary">
     1090                    ← <?php esc_html_e('Back to Overview', 'artidomo-print-on-demand'); ?>
    10841091                </a>
    10851092            </div>
    10861093
    10871094            <div class="artidomo-card">
    1088                 <h3>🏷️ Alle Produktzuordnungen (<?php echo $total_products; ?> Produkte)</h3>
     1095                <h3>🏷️ <?php
     1096                    /* translators: %d: number of products */
     1097                    printf(esc_html__('All Product Mappings (%d products)', 'artidomo-print-on-demand'), $total_products);
     1098                ?></h3>
    10891099
    10901100                <p style="color: #666; margin-bottom: 20px; font-size: 13px;">
    1091                     Hier kannst Du alle Produktzuordnungen einsehen. Du kannst die Zuordnung besser im Fulfillment-Portal vornehmen. Aber es geht auch in WooCommerce unter den Produkten: Bei Einzelprodukten unter dem Reiter "artidomo" und bei Varianten-Produkten direkt in der Variante selbst.
     1101                    <?php esc_html_e('Here you can view all product mappings. You can manage mappings better in the Fulfillment Portal. But you can also do it in WooCommerce under Products: For simple products under the "artidomo" tab and for variable products directly in the variation.', 'artidomo-print-on-demand'); ?>
    10921102                </p>
    10931103
    10941104                <?php if (empty($products)): ?>
    10951105                    <p style="text-align: center; padding: 40px; color: #999;">
    1096                         Keine Produktzuordnungen gefunden.
     1106                        <?php esc_html_e('No product mappings found.', 'artidomo-print-on-demand'); ?>
    10971107                    </p>
    10981108                <?php else: ?>
     
    11011111                            <thead>
    11021112                                <tr style="background: #f9f9f9;">
    1103                                     <th style="width: 60px; padding: 12px; font-weight: 600;">ID</th>
    1104                                     <th style="padding: 12px; font-weight: 600;">Produktname</th>
    1105                                     <th style="padding: 12px; font-weight: 600;">WooCommerce SKU</th>
    1106                                     <th style="width: 150px; padding: 12px; font-weight: 600;">artidomo SKU</th>
    1107                                     <th style="width: 120px; padding: 12px; font-weight: 600;">WooCommerce Preis (netto)</th>
    1108                                     <th style="width: 120px; padding: 12px; font-weight: 600;">artidomo Preis (netto)</th>
    1109                                     <th style="width: 150px; padding: 12px; font-weight: 600;">Druckdatei</th>
    1110                                     <th style="width: 100px; padding: 12px; font-weight: 600;">Aktion</th>
     1113                                    <th style="width: 60px; padding: 12px; font-weight: 600;"><?php esc_html_e('ID', 'artidomo-print-on-demand'); ?></th>
     1114                                    <th style="padding: 12px; font-weight: 600;"><?php esc_html_e('Product Name', 'artidomo-print-on-demand'); ?></th>
     1115                                    <th style="padding: 12px; font-weight: 600;"><?php esc_html_e('WooCommerce SKU', 'artidomo-print-on-demand'); ?></th>
     1116                                    <th style="width: 150px; padding: 12px; font-weight: 600;"><?php esc_html_e('artidomo SKU', 'artidomo-print-on-demand'); ?></th>
     1117                                    <th style="width: 120px; padding: 12px; font-weight: 600;"><?php esc_html_e('WooCommerce Price (net)', 'artidomo-print-on-demand'); ?></th>
     1118                                    <th style="width: 120px; padding: 12px; font-weight: 600;"><?php esc_html_e('artidomo Price (net)', 'artidomo-print-on-demand'); ?></th>
     1119                                    <th style="width: 150px; padding: 12px; font-weight: 600;"><?php esc_html_e('Print File', 'artidomo-print-on-demand'); ?></th>
     1120                                    <th style="width: 100px; padding: 12px; font-weight: 600;"><?php esc_html_e('Action', 'artidomo-print-on-demand'); ?></th>
    11111121                                </tr>
    11121122                            </thead>
     
    11201130                                    $artidomo_sku = get_post_meta($product_id, '_artidomo_sku', true);
    11211131                                    $printfilename = get_post_meta($product_id, '_artidomo_printfilename', true);
    1122                                     $personalization_provider = get_post_meta($product_id, '_artidomo_personalization_provider', true);
    1123 
    1124                                     // WooCommerce Preis (netto)
     1132
     1133                                    // WooCommerce Price (net)
    11251134                                    $woo_price_incl = $product->get_price();
    11261135                                    $woo_price_net = $this->calculate_net_price($woo_price_incl, $product);
    11271136
    1128                                     // artidomo Preis
     1137                                    // artidomo Price
    11291138                                    $artidomo_price = isset($artidomo_prices[$artidomo_sku]) ? $artidomo_prices[$artidomo_sku] : null;
    11301139
     
    11351144                                ?>
    11361145                                <tr style="border-bottom: 1px solid #eee;">
    1137                                     <td style="padding: 12px;"><?php echo $product_id; ?></td>
     1146                                    <td style="padding: 12px;"><?php echo esc_html($product_id); ?></td>
    11381147                                    <td style="padding: 12px;">
    11391148                                        <strong><?php echo esc_html($product->get_name()); ?></strong>
    11401149                                        <?php if ($is_variation): ?>
    1141                                             <br><small style="color: #999;">↳ Variante von #<?php echo $product->get_parent_id(); ?></small>
     1150                                            <br><small style="color: #999;">↳ <?php
     1151                                                /* translators: %d: parent product ID */
     1152                                                printf(esc_html__('Variation of #%d', 'artidomo-print-on-demand'), $product->get_parent_id());
     1153                                            ?></small>
    11421154                                        <?php endif; ?>
    11431155                                    </td>
     
    11451157                                    <td style="padding: 12px;"><code style="background: #f0f0f0; padding: 4px 8px; border-radius: 3px; font-size: 11px;"><?php echo esc_html($artidomo_sku); ?></code></td>
    11461158                                    <td style="padding: 12px; font-weight: 600; color: #2271b1;">
    1147                                         <?php echo $woo_price_net !== null ? wc_price($woo_price_net) : '—'; ?>
     1159                                        <?php echo $woo_price_net !== null ? wp_kses_post(wc_price($woo_price_net)) : '—'; ?>
    11481160                                    </td>
    11491161                                    <td style="padding: 12px; font-weight: 600; color: #3c8735;">
    11501162                                        <?php
    11511163                                        if ($artidomo_price !== null) {
    1152                                             echo wc_price($artidomo_price);
     1164                                            echo wp_kses_post(wc_price($artidomo_price));
    11531165                                        } else {
    11541166                                            echo '<span style="color: #999;">—</span>';
     
    11581170                                    <td style="padding: 12px; font-size: 12px; color: #666;"><?php echo esc_html($printfilename ?: '—'); ?></td>
    11591171                                    <td style="padding: 12px;">
    1160                                         <a href="<?php echo $edit_url; ?>" class="button button-small" style="font-size: 11px; padding: 4px 8px;">
    1161                                             ✏️ Bearbeiten
     1172                                        <a href="<?php echo esc_url($edit_url); ?>" class="button button-small" style="font-size: 11px; padding: 4px 8px;">
     1173                                            ✏️ <?php esc_html_e('Edit', 'artidomo-print-on-demand'); ?>
    11621174                                        </a>
    11631175                                    </td>
     
    11731185                                <div class="tablenav-pages">
    11741186                                    <?php
    1175                                     echo paginate_links(array(
     1187                                    echo wp_kses_post(paginate_links(array(
    11761188                                        'base' => add_query_arg('paged', '%#%'),
    11771189                                        'format' => '',
    11781190                                        'current' => $current_page,
    11791191                                        'total' => $total_pages,
    1180                                         'prev_text' => '&laquo; Zurück',
    1181                                         'next_text' => 'Weiter &raquo;',
    1182                                     ));
     1192                                        'prev_text' => '&laquo; ' . __('Back', 'artidomo-print-on-demand'),
     1193                                        'next_text' => __('Next', 'artidomo-print-on-demand') . ' &raquo;',
     1194                                    )));
    11831195                                    ?>
    11841196                                </div>
     
    11931205
    11941206    /**
    1195      * Berechne Netto-Preis aus WooCommerce Preis
     1207     * Calculate Net Price from WooCommerce Price
    11961208     */
    11971209    private function calculate_net_price($price, $product) {
     
    12001212        }
    12011213
    1202         // Prüfe ob WooCommerce Preis inkl. MwSt. ist
     1214        // Check if WooCommerce price includes tax
    12031215        $tax_status = $product->get_tax_status();
    12041216        $tax_class = $product->get_tax_class();
    12051217
    12061218        if ($tax_status === 'taxable' && wc_prices_include_tax()) {
    1207             // Preis ist brutto, konvertiere zu netto
     1219            // Price is gross, convert to net
    12081220            $tax_rates = WC_Tax::get_rates($tax_class);
    12091221
     
    12161228        }
    12171229
    1218         // Preis ist bereits netto oder keine Steuer
     1230        // Price is already net or no tax
    12191231        return floatval($price);
    12201232    }
    12211233
    12221234    /**
    1223      * Hole artidomo Preise aus dem Backend
     1235     * Get artidomo prices from Backend
    12241236     */
    12251237    private function get_artidomo_prices() {
    1226         // Cache für 5 Minuten
     1238        // Cache for 5 minutes
    12271239        $cache_key = 'artidomo_prices_cache';
    12281240        $cached = get_transient($cache_key);
     
    12321244        }
    12331245
    1234         // Hole Preise vom artidomo Backend
     1246        // Get prices from artidomo Backend
    12351247        $response = wp_remote_get(ARTIDOMO_API_URL . '/products/prices', array(
    12361248            'timeout' => 10,
  • artidomo-print-on-demand/trunk/readme.txt

    r3430729 r3431054  
    11=== artidomo Print on Demand ===
    22Contributors: artidomo
    3 Tags: print on demand, woocommerce, fulfillment, poster, print
     3Tags: print on demand, woocommerce, fulfillment, poster, print, dropshipping, german
    44Requires at least: 5.8
    55Tested up to: 6.7
     
    99License URI: https://www.gnu.org/licenses/gpl-2.0.html
    1010
    11 Verbindet WooCommerce mit dem artidomo Fulfillment System. Automatische Auftragsverarbeitung für Poster, Leinwände und personalisierte Druckprodukte.
     11Connect WooCommerce to the artidomo Fulfillment System. Automatic order processing for posters, canvases, and personalized print products.
    1212
    1313== Description ==
    1414
    15 **artidomo Print on Demand** ist die offizielle Erweiterung zur Anbindung deines WooCommerce-Shops an das artidomo Fulfillment-System.
     15**artidomo Print on Demand** is the official extension for connecting your WooCommerce shop to the artidomo fulfillment system.
    1616
    17 = Was ist artidomo? =
     17**Fully translated: English and German (Deutsch)**
    1818
    19 artidomo ist ein deutscher Print-on-Demand Dienstleister spezialisiert auf:
     19= What is artidomo? =
    2020
    21 * **Poster & Fine Art Prints** - Museum-Qualität auf verschiedenen Papieren
    22 * **Leinwandbilder** - Fertig bespannt, verschiedene Formate
    23 * **Wandbilder** - Alu-Dibond, Acrylglas, Forex
    24 * **Personalisierte Produkte** - Mit Kundentext, Namen oder Bildern
     21artidomo is a German Print-on-Demand service provider specializing in:
    2522
    26 = Funktionen =
     23* **Posters & Fine Art Prints** - Museum quality on various papers
     24* **Canvas Prints** - Ready-to-hang, various sizes
     25* **Wall Art** - Aluminum Dibond, Acrylic Glass, Forex
     26* **Personalized Products** - With customer text, names, or images
    2727
    28 * **One-Click-Verbindung** - Verbinde deinen Shop in Sekunden mit dem artidomo Portal
    29 * **Automatische Auftragsübertragung** - Bezahlte Bestellungen werden automatisch an artidomo gesendet
    30 * **Produktzuordnung** - Einfache Zuordnung deiner Produkte zu artidomo-Artikeln
    31 * **Webhook-Integration** - Echtzeit-Statusaktualisierungen
    32 * **German Market & Germanized Support** - Volle Kompatibilität mit deutschen WooCommerce-Plugins
    33 * **HPOS-Kompatibel** - Unterstützt WooCommerce High-Performance Order Storage
    34 * **CSV Import/Export** - Massenzuordnung von Produkten
     28= Features =
    3529
    36 = Voraussetzungen =
     30* **One-Click Connection** - Connect your shop to the artidomo Portal in seconds
     31* **Automatic Order Transfer** - Paid orders are automatically sent to artidomo
     32* **Product Mapping** - Easily map your products to artidomo items
     33* **Webhook Integration** - Real-time status updates
     34* **German Market & Germanized Support** - Full compatibility with German WooCommerce plugins
     35* **HPOS Compatible** - Supports WooCommerce High-Performance Order Storage
     36* **CSV Import/Export** - Bulk product mapping
    3737
    38 * WooCommerce 5.0 oder höher
    39 * PHP 7.4 oder höher
    40 * WordPress 5.8 oder höher
    41 * Ein aktiver artidomo-Vertrag ([portal.artidomo.eu](https://portal.artidomo.eu))
     38= Requirements =
    4239
    43 = Datenschutz =
     40* WooCommerce 5.0 or higher
     41* PHP 7.4 or higher
     42* WordPress 5.8 or higher
     43* An active artidomo contract ([portal.artidomo.eu](https://portal.artidomo.eu))
    4444
    45 Durch die Verbindung mit artidomo werden Bestelldaten (Lieferadresse, Bestellpositionen) an die Server von artidomo (portal.artidomo.eu) übermittelt. Dies ist für die Auftragsabwicklung erforderlich. Eine Auftragsverarbeitungsvereinbarung (AVV) ist Bestandteil des artidomo-Vertrags.
     45= Privacy =
     46
     47By connecting to artidomo, order data (shipping address, order items) is transmitted to artidomo servers (portal.artidomo.eu). This is required for order fulfillment. A Data Processing Agreement (DPA) is part of the artidomo contract.
     48
     49= Sprache / Language =
     50
     51This plugin is fully translated into German. The admin interface will automatically display in German when your WordPress installation uses German (de_DE).
     52
     53Dieses Plugin ist vollständig auf Deutsch übersetzt. Die Admin-Oberfläche wird automatisch auf Deutsch angezeigt, wenn deine WordPress-Installation Deutsch verwendet.
    4654
    4755== Installation ==
    4856
    49 = Automatische Installation =
     57= Automatic Installation =
    5058
    51 1. Gehe im WordPress-Admin zu **Plugins → Installieren**
    52 2. Suche nach "artidomo"
    53 3. Klicke auf **Jetzt installieren**
    54 4. Aktiviere das Plugin
     591. Go to **Plugins → Add New** in WordPress Admin
     602. Search for "artidomo"
     613. Click **Install Now**
     624. Activate the plugin
    5563
    56 = Manuelle Installation =
     64= Manual Installation =
    5765
    58 1. Lade die ZIP-Datei herunter
    59 2. Gehe zu **Plugins → Installieren → Plugin hochladen**
    60 3. Wähle die ZIP-Datei aus und klicke auf **Jetzt installieren**
    61 4. Aktiviere das Plugin
     661. Download the ZIP file
     672. Go to **Plugins → Add New → Upload Plugin**
     683. Select the ZIP file and click **Install Now**
     694. Activate the plugin
    6270
    63 = Nach der Installation =
     71= After Installation =
    6472
    65 1. Gehe zu **WooCommerce → artidomo**
    66 2. Melde dich im artidomo Portal an oder registriere dich
    67 3. Klicke im Portal auf "Shop hinzufügen" und wähle WooCommerce
    68 4. Die Verbindung wird automatisch hergestellt
    69 5. Ordne deine Produkte den artidomo-Artikeln zu
     731. Go to **WooCommerce → artidomo**
     742. Log in to the artidomo Portal or register
     753. Click "Add Shop" in the Portal and select WooCommerce
     764. The connection will be established automatically
     775. Map your products to artidomo items
    7078
    7179== Frequently Asked Questions ==
    7280
    73 = Benötige ich einen artidomo-Account? =
     81= Do I need an artidomo account? =
    7482
    75 Ja, du benötigst einen aktiven Vertrag mit artidomo. Registriere dich kostenlos unter [portal.artidomo.eu](https://portal.artidomo.eu).
     83Yes, you need an active contract with artidomo. Register for free at [portal.artidomo.eu](https://portal.artidomo.eu).
    7684
    77 = Wie funktioniert die Auftragsübertragung? =
     85= How does order transfer work? =
    7886
    79 Sobald eine Bestellung in WooCommerce als "bezahlt" markiert wird (Status "Processing" oder "Completed"), wird sie automatisch per Webhook an artidomo übertragen. Dort wird sie produziert und direkt an deinen Kunden versendet.
     87When an order is marked as "paid" in WooCommerce (status "Processing" or "Completed"), it is automatically transferred to artidomo via webhook. There it is produced and shipped directly to your customer.
    8088
    81 = Welche Produkte kann ich mit artidomo verkaufen? =
     89= What products can I sell with artidomo? =
    8290
    83 artidomo bietet eine große Auswahl an Druckprodukten:
     91artidomo offers a wide range of print products:
    8492
    85 * Poster (Matt, Glanz, Fine Art)
    86 * Leinwandbilder (verschiedene Größen und Rahmen)
    87 * Wandbilder (Alu-Dibond, Acrylglas, Forex)
    88 * Personalisierte Produkte mit Kundentext oder -bild
     93* Posters (Matte, Glossy, Fine Art)
     94* Canvas Prints (various sizes and frames)
     95* Wall Art (Aluminum Dibond, Acrylic Glass, Forex)
     96* Personalized products with customer text or images
    8997
    90 = Funktioniert das Plugin mit German Market oder Germanized? =
     98= Does the plugin work with German Market or Germanized? =
    9199
    92 Ja! Das Plugin erkennt automatisch German Market und Germanized und passt sich an die spezifischen Bestellstatus dieser Plugins an.
     100Yes! The plugin automatically detects German Market and Germanized and adapts to the specific order statuses of these plugins.
    93101
    94 = Kann ich eigene Druckdateien verwenden? =
     102= Can I use my own print files? =
    95103
    96 Ja, du kannst deine eigenen Druckdateien im artidomo Portal hochladen und mit deinen Produkten verknüpfen.
     104Yes, you can upload your own print files in the artidomo Portal and link them to your products.
    97105
    98 = Wie werden die Versandkosten berechnet? =
     106= How are shipping costs calculated? =
    99107
    100 Die Versandkosten werden nach dem artidomo-Preissystem berechnet. Details findest du in deinem artidomo-Vertrag.
     108Shipping costs are calculated according to the artidomo pricing system. Details can be found in your artidomo contract.
    101109
    102 = Was passiert bei Retouren? =
     110= What happens with returns? =
    103111
    104 Retouren und Reklamationen werden über das artidomo Portal abgewickelt. Bei Druckfehlern erfolgt eine kostenlose Neuproduktion.
     112Returns and complaints are handled through the artidomo Portal. Printing errors result in free reproduction.
    105113
    106114== Screenshots ==
    107115
    108 1. Shop-Verbindung - Einfache Anbindung an das artidomo System
    109 2. Produktzuordnung - Verknüpfe WooCommerce-Produkte mit artidomo-Artikeln
    110 3. Bestellübersicht - Alle übertragenen Bestellungen im Blick
    111 4. Einstellungen - Webhook-Konfiguration und Plugin-Status
     1161. Shop Connection - Easy connection to the artidomo system
     1172. Product Mapping - Link WooCommerce products to artidomo items
     1183. Order Overview - Track all transferred orders
     1194. Settings - Webhook configuration and plugin status
    112120
    113121== Changelog ==
    114122
    115123= 2.0.0 =
    116 * Neu: Vollständige Überarbeitung für wordpress.org
    117 * Neu: Verbesserter Update-Mechanismus
    118 * Neu: HPOS-Kompatibilität (WooCommerce High-Performance Order Storage)
    119 * Neu: Erweiterte German Market & Germanized Unterstützung
    120 * Neu: CSV-Massenimport/-export für Produktzuordnungen
    121 * Neu: Verbesserte Admin-Oberfläche
    122 * Fix: Block-Checkout-Kompatibilität verbessert
    123 * Fix: Hausnummer-Extraktion optimiert
     124* New: Complete redesign for wordpress.org
     125* New: Improved update mechanism
     126* New: HPOS compatibility (WooCommerce High-Performance Order Storage)
     127* New: Extended German Market & Germanized support
     128* New: CSV bulk import/export for product mappings
     129* New: Improved admin interface
     130* New: Full English and German translations
     131* Fix: Block checkout compatibility improved
     132* Fix: House number extraction optimized
    124133
    125134= 1.0.0 =
    126 * Erste Version
     135* Initial release
    127136
    128137== Upgrade Notice ==
    129138
    130139= 2.0.0 =
    131 Große Überarbeitung mit verbesserter Kompatibilität und neuen Funktionen. Empfohlenes Update für alle Nutzer.
     140Major redesign with improved compatibility and new features. Recommended update for all users.
    132141
    133142== Additional Info ==
     
    135144= Support =
    136145
    137 Bei Fragen wende dich an [[email protected]](mailto:[email protected]) oder besuche das [artidomo Portal](https://portal.artidomo.eu).
     146For questions, contact [[email protected]](mailto:[email protected]) or visit the [artidomo Portal](https://portal.artidomo.eu).
    138147
    139 = Über artidomo =
     148= About artidomo =
    140149
    141 artidomo ist ein deutscher Print-on-Demand Dienstleister mit Sitz in Bochum. Wir produzieren hochwertige Druckprodukte und versenden diese direkt an deine Kunden - weltweit.
     150artidomo is a German Print-on-Demand service provider based in Bochum, Germany. We produce high-quality print products and ship them directly to your customers - worldwide.
    142151
    143 **Kontakt:**
    144 artidomo - Inhaberin: Marina Scheubly
    145 Wittener Str. 75, 44789 Bochum
    146 Tel: +49-(0)234-52009829
    147 E-Mail: [email protected]
     152**Contact:**
     153artidomo - Owner: Marina Scheubly
     154Wittener Str. 75, 44789 Bochum, Germany
     155Phone: +49-(0)234-52009829
     156Email: [email protected]
    148157Web: [www.artidomo.eu](https://www.artidomo.eu)
Note: See TracChangeset for help on using the changeset viewer.