/**
 * Component for selecting node columns based on the current form state
 */
import { ErrorMessage, useFormikContext } from 'formik';
import { useContext, useMemo, useState, useEffect } from 'react';
import DJClientContext from '../../providers/djclient';
import { FormikSelect } from './FormikSelect';

export const ColumnsSelect = ({
  defaultValue,
  fieldName,
  label,
  labelStyle = {},
  isMulti = false,
  isClearable = true,
}) => {
  const djClient = useContext(DJClientContext).DataJunctionAPI;

  // Used to pull out current form values for node validation
  const { values } = useFormikContext();

  // The available columns, determined from validating the node query
  const [availableColumns, setAvailableColumns] = useState([]);
  const [validationError, setValidationError] = useState(null);
  const selectableOptions = useMemo(() => {
    if (availableColumns && availableColumns.length > 0) {
      return availableColumns;
    }
    return [];
  }, [availableColumns]);

  // Fetch columns by validating the latest node query
  const fetchColumns = async () => {
    try {
      const { status, json } = await djClient.validateNode(
        values.type,
        values.name,
        values.display_name,
        values.description,
        values.query,
      );
      if (json?.columns) {
        setAvailableColumns(
          json.columns.map(col => ({ value: col.name, label: col.name })),
        );
        setValidationError(null);
      } else {
        // Prefer the structured per-error messages (e.g. parse failures with
        // INVALID_SQL_QUERY) over the generic `Node X is invalid.` summary.
        const detailed = Array.isArray(json?.errors)
          ? json.errors
              .map(e => e.message)
              .filter(Boolean)
              .join('\n')
          : '';
        setValidationError(detailed || json?.message || null);
        setAvailableColumns([]);
      }
    } catch (error) {
      console.error('Error fetching columns:', error);
      setValidationError(
        error.message ||
          'Failed to validate query. Please check your query syntax.',
      );
      setAvailableColumns([]);
    }
  };

  useEffect(() => {
    fetchColumns();
  }, [values.type, values.name, values.query]);

  return (
    <div className="CubeCreationInput">
      <ErrorMessage name={fieldName} component="span" />
      <label htmlFor={fieldName} style={labelStyle}>
        {label}
      </label>
      {validationError && (
        <div
          className="validation-error"
          style={{
            color: '#d32f2f',
            fontSize: '0.875rem',
            marginBottom: '8px',
            padding: '8px',
            backgroundColor: '#ffebee',
            borderRadius: '4px',
            border: '1px solid #ef9a9a',
          }}
        >
          <strong>Validation Error:</strong> {validationError}
        </div>
      )}
      <span data-testid={`select-${fieldName}`}>
        <FormikSelect
          className=""
          defaultValue={
            isMulti
              ? defaultValue.map(val => {
                  return {
                    value: val,
                    label: val,
                  };
                })
              : defaultValue
              ? { value: defaultValue, label: defaultValue }
              : null
          }
          selectOptions={selectableOptions}
          formikFieldName={fieldName}
          onFocus={event => fetchColumns(event)}
          isMulti={isMulti}
          isClearable={isClearable}
        />
      </span>
    </div>
  );
};
