Skip to content
← Back to Functions
Code

CSV Encoding Normalizer

Detects and normalizes CSV content to UTF-8 while preserving accents.

Function signature

ogNormalizeCsvEncoding(csv_contents, source_encoding = '')

Categories

  • Import and Export

Parameters

csv_contentsRaw CSV file contents.source_encodingOptional known source encoding.

Return value

Short public-safe status message.

  • contents
  • source_encoding
  • byte_length

Compatibility

Existing function name and call order preserved; metadata signature corrected to source.

Minimum PHP version: 7.4

Security notes

Validate request method, identity, permissions, and caller-owned allowlists before use; keep secrets and internal paths out of public output.

Code

<?php

/*
 * Copyright (c) 2026 Jeffery L. Paris <jparis@phpog.com>.
 * Free for personal and internal use. Paid project use requires visible credit
 * to Jeffery L. Paris. Corporate use requires a paid license fee unless a
 * separate written license states otherwise.
 */

/**
 * Normalizes CSV content to UTF-8 while preserving valid accent characters.
 *
 * The function removes a UTF-8 BOM and uses mbstring or iconv when available.
 * It does not strip non-ASCII text.
 *
 * @param string $csv_contents Raw CSV file contents.
 * @param string $source_encoding Optional known source encoding.
 * @return array Structured result with normalized CSV contents and encoding metadata.
 */
function ogNormalizeCsvEncoding($csv_contents, $source_encoding = '') {
	$result = array(
		'success' => false,
		'message' => '',
		'data' => array()
	);

	$csv_contents = (string)$csv_contents;
	$source_encoding = trim((string)$source_encoding);

	if ($csv_contents === '') {
		$result['message'] = 'CSV contents are empty.';
		return $result;
	}

	$csv_contents = preg_replace('/^\xEF\xBB\xBF/', '', $csv_contents);
	$detected_encoding = $source_encoding;

	if (empty($detected_encoding) && function_exists('mb_detect_encoding')) {
		$detected = mb_detect_encoding($csv_contents, array('UTF-8', 'Windows-1252', 'ISO-8859-1', 'ASCII'), true);
		if (!empty($detected)) {
			$detected_encoding = $detected;
		}
	}

	if (empty($detected_encoding)) {
		$detected_encoding = 'UTF-8';
	}

	$normalized = $csv_contents;
	if (strtoupper($detected_encoding) != 'UTF-8') {
		if (function_exists('mb_convert_encoding')) {
			$normalized = mb_convert_encoding($csv_contents, 'UTF-8', $detected_encoding);
		} elseif (function_exists('iconv')) {
			$converted = iconv($detected_encoding, 'UTF-8//TRANSLIT', $csv_contents);
			if ($converted !== false) {
				$normalized = $converted;
			}
		}
	}

	$result['success'] = true;
	$result['message'] = 'CSV encoding normalized.';
	$result['data'] = array(
		'contents' => $normalized,
		'source_encoding' => $detected_encoding,
		'byte_length' => strlen($normalized)
	);

	return $result;
}