/**
 * Example code demonstrating the use of special field validators
 */
import { z } from 'zod';
import {
  User,
  Location,
  Server,
  Contact,
  Order,
  OrderItem,
  Product,
  WebsiteConfig,
  LoginCredentials,
  PasswordReset,
  GeoPoint,
  // New types with pattern-based field validators
  EcommerceProduct,
  ProductDimensions,
  UserActivity,
  Transaction,
  Theme,
  AnalyticsData,
  ShippingOrder
} from './types';

// Import the automatically generated Zod schemas
// In a real application, these would be generated by the type-compiler
// For this example, we're importing them as if they were generated
import {
  zUser,
  zLocation,
  zServer,
  zContact,
  zOrder,
  zOrderItem,
  zProduct,
  zWebsiteConfig,
  zLoginCredentials,
  zPasswordReset,
  zGeoPoint,
  // New schemas
  zEcommerceProduct,
  zProductDimensions,
  zUserActivity,
  zTransaction,
  zTheme,
  zAnalyticsData,
  zShippingOrder
} from './schemas';

// Example data
const validUser: User = {
  uuid: '123e4567-e89b-12d3-a456-426614174000',
  username: 'johndoe',
  email: 'john.doe@example.com',
  password: 'P@ssw0rd!',
  birthDate: '1990-01-01',
  age: 33,
  profileUrl: 'https://example.com/users/johndoe',
  phoneNumber: '+12125551234',
  createdAt: new Date()
};

const invalidUser = {
  uuid: 'not-a-uuid',
  username: 'a',  // too short
  email: 'not-an-email',
  password: 'weak',  // fails complexity requirements
  birthDate: 'yesterday',  // invalid date format
  age: 200,  // outside the allowed range
  profileUrl: 'not-a-url',
  phoneNumber: '123',  // invalid phone number format
  createdAt: 'now'  // not a Date
};

const validLocation: Location = {
  name: 'Central Park',
  latitude: 40.7812,
  longitude: -73.9665,
  address: '59th to 110th St., New York, NY',
  zipCode: '10022'
};

const validGeoPoint: GeoPoint = {
  latitude: 40.7812,
  longitude: -73.9665,
  elevation: 100
};

// Function to validate data and print results
function validateAndPrint(schema: z.ZodType<any>, data: any, label: string): void {
  console.log(`\n--- Validating ${label} ---`);
  try {
    const validated = schema.parse(data);
    console.log('✅ Valid data:', JSON.stringify(validated, null, 2));
  } catch (error) {
    if (error instanceof z.ZodError) {
      console.log('❌ Validation errors:');
      error.errors.forEach(err => {
        console.log(`- ${err.path.join('.')}: ${err.message}`);
      });
    } else {
      console.error('Unexpected error:', error);
    }
  }
}

// Main function to demonstrate the validation
function main() {
  console.log('=== Special Field Validators Example ===');
  console.log('This example demonstrates how the type-compiler uses special field validators\n');
  
  // Validate valid user
  validateAndPrint(zUser, validUser, 'Valid User');
  
  // Validate invalid user
  validateAndPrint(zUser, invalidUser, 'Invalid User');
  
  // Validate location with latitude/longitude
  validateAndPrint(zLocation, validLocation, 'Valid Location');
  
  // Validate GeoPoint - should use the same validators for latitude/longitude
  validateAndPrint(zGeoPoint, validGeoPoint, 'Valid GeoPoint');
  
  // Demonstrate multiple interfaces with the same special field
  const contact: Contact = {
    firstName: 'Jane',
    lastName: 'Smith',
    email: 'jane.smith@example.com',
    phoneNumber: '+12125551234',
    address: '123 Main St, New York, NY'
  };
  
  validateAndPrint(zContact, contact, 'Contact with email and phone');
  
  // Login credentials with email and password
  const credentials: LoginCredentials = {
    email: 'user@example.com',
    password: 'SecureP@ss123!'
  };
  
  validateAndPrint(zLoginCredentials, credentials, 'Login Credentials');
  
  // Demonstrate more complex validation chains
  const server: Server = {
    hostname: 'api-server',
    ipAddress: '192.168.1.1',
    url: 'https://api.example.com',
    port: 443,
    lastChecked: new Date()
  };
  
  validateAndPrint(zServer, server, 'Server');
  
  console.log('\n=== Pattern-Based Field Validation Examples ===');
  console.log('These examples demonstrate how pattern-based field validators work\n');
  
  // Demonstration of E-commerce product with various field patterns
  const validProduct: EcommerceProduct = {
    productId: 'prod-123',
    sku: 'SKU-123-456',
    name: 'Wireless Headphones',
    description: 'Premium wireless headphones with noise cancellation',
    basePrice: 99.99,
    discountAmount: 20,
    totalPrice: 79.99,
    taxRate: 8.5,
    stockCount: 42,
    dimensions: {
      width: 8.5,
      height: 7.2,
      depth: 3.1,
      weight: 0.35,
      sizeCategory: 'medium'
    },
    availableColors: ['black', 'white', 'blue'],
    primaryColor: '#3366FF',
    tags: ['electronics', 'audio', 'wireless'],
    categories: ['headphones', 'accessories'],
    isAvailable: true,
    hasVariants: true,
    productStatus: 'active',
    createdAt: new Date(),
    updatedAt: new Date()
  };
  
  validateAndPrint(zEcommerceProduct, validProduct, 'E-commerce Product (valid)');
  
  // Invalid product demo
  const invalidProduct = {
    ...validProduct,
    basePrice: -10,               // Invalid: negative price
    taxRate: 120,                 // Invalid: rate > 100
    stockCount: -5,               // Invalid: negative count
    primaryColor: 'blue',         // Invalid: not a valid color format
    dimensions: {
      ...validProduct.dimensions,
      width: -1,                  // Invalid: negative dimension
    },
    productStatus: 'unknown',     // Valid: string is accepted as fallback for enum
  };
  
  validateAndPrint(zEcommerceProduct, invalidProduct, 'E-commerce Product (invalid)');
  
  // User activity with timestamps, counts, and booleans
  const validActivity: UserActivity = {
    activityId: 'act-123456',
    userId: 'user-789',
    sessionId: 'sess-456',
    activityType: 'page_view',
    startTime: new Date('2023-06-01T10:30:00Z'),
    endTime: new Date('2023-06-01T10:35:00Z'),
    loginDate: '2023-06-01',      // String date that will be coerced
    durationSeconds: 300,
    completionRate: 85.5,
    clickCount: 12,
    pageViewCount: 7,
    isCompleted: true,
    canResume: false,
    activityStatus: 'completed'
  };
  
  validateAndPrint(zUserActivity, validActivity, 'User Activity (valid)');
  
  // Financial transaction with monetary values and rates
  const validTransaction: Transaction = {
    transactionId: 'tx-789012',
    referenceCode: 'ref-12345',
    amount: 250.75,
    fee: 2.99,
    totalAmount: 253.74,
    interestRate: 4.5,
    exchangeRate: 1.23,
    transactionDate: new Date('2023-05-15'),
    processedAt: new Date(),
    shouldNotify: true,
    transactionStatus: 'completed'
  };
  
  validateAndPrint(zTransaction, validTransaction, 'Financial Transaction (valid)');
  
  // UI Theme with color validations
  const validTheme: Theme = {
    themeId: 'theme-dark',
    name: 'Dark Mode',
    primaryColor: '#121212',
    secondaryColor: '#333333',
    backgroundColor: '#000000',
    textColor: '#FFFFFF',
    accentColor: '#4285F4',
    isDefault: false,
    createdAt: new Date()
  };
  
  validateAndPrint(zTheme, validTheme, 'UI Theme (valid)');
  
  // Analytics data with count and rate validations
  const validAnalytics: AnalyticsData = {
    metricId: 'metric-123',
    pageId: 'page-home',
    visitorCount: 5421,
    conversionCount: 127,
    bounceCount: 1834,
    conversionRate: 2.34,
    bounceRate: 33.8,
    engagementRatio: 42.1,
    recordedAt: new Date(),
    periodStartDate: '2023-06-01',
    periodEndDate: '2023-06-30',
    isRealTime: false,
    dataStatus: 'completed'
  };
  
  validateAndPrint(zAnalyticsData, validAnalytics, 'Analytics Data (valid)');
  
  // Shipping order with status and dimension validations
  const validOrder: ShippingOrder = {
    orderId: 'order-123456',
    trackingCode: 'track-789012',
    shippingStatus: 'pending',
    paymentStatus: 'completed',
    orderStatus: 'processing',
    shippingCost: 12.99,
    packageWidth: 30,
    packageHeight: 20,
    packageLength: 40,
    orderDate: new Date('2023-06-15'),
    shipByDate: new Date('2023-06-18'),
    deliveryTime: '2023-06-20T14:00:00Z',
    isExpress: true,
    hasInsurance: true,
    items: ['item1', 'item2', 'item3']
  };
  
  validateAndPrint(zShippingOrder, validOrder, 'Shipping Order (valid)');
  
  // Invalid dimension values
  const invalidOrderDimensions = {
    ...validOrder,
    packageWidth: -5,      // Invalid: negative dimension
    packageHeight: 0       // Invalid: zero dimension
  };
  
  validateAndPrint(zShippingOrder, invalidOrderDimensions, 'Shipping Order (invalid dimensions)');

  console.log('\n=== Pattern Matching Summary ===');
  console.log('The pattern-based field validators automatically applied appropriate validation rules based on field naming patterns:');
  console.log('- Fields ending with "Id" or "Code" → string validation');
  console.log('- Fields containing "price", "amount", "cost", etc. → monetary value validation');
  console.log('- Fields ending with "Count" → positive integer validation');
  console.log('- Fields matching dimension patterns (width, height, etc.) → positive number validation');
  console.log('- Fields starting with "is", "has", "can", "should" → boolean validation');
  console.log('- Fields ending with "Color" → color format validation');
  console.log('- Fields ending with "Status" → enum validation with string fallback');
  console.log('- Fields ending with "At", "Date", "Time" → date validation with coercion');
  console.log('- Fields ending with "Percent", "Rate", "Ratio" → 0-100 range validation');
  console.log('- Fields matching array patterns (tags, categories, etc.) → array validation');
  
  console.log('\n=== Validation Complete ===');
}

// Run the main function
main(); 