Привет. Я пытаюсь сохранить имена в базе данных Oracle и получить их обратно, используя PHP и oci8.
Однако, если я вставлю é
непосредственно в базу данных Oracle и использую oci8, чтобы получить его обратноЯ просто получаю e
Нужно ли мне кодировать все специальные символы (включая é
) в HTML-сущности (т.е.: é
) перед вставкой в базу данных ... или я что-то упустил?
Thx
ОБНОВЛЕНИЕ: 1 марта в 18: 40
нашел эту функцию: http://www.php.net/manual/en/function.utf8-decode.php#85034
function charset_decode_utf_8($string) {
if(@!ereg("[\200-\237]",$string) && @!ereg("[\241-\377]",$string)) {
return $string;
}
$string = preg_replace("/([\340-\357])([\200-\277])([\200-\277])/e","'&#'.((ord('\\1')-224)*4096 + (ord('\\2')-128)*64 + (ord('\\3')-128)).';'",$string);
$string = preg_replace("/([\300-\337])([\200-\277])/e","'&#'.((ord('\\1')-192)*64+(ord('\\2')-128)).';'",$string);
return $string;
}
, кажется, работает, хотя и не уверен, что это оптимальное решение
ОБНОВЛЕНИЕ: 8 марта в 15: 45
Набор символов Oracle - ISO-8859-1.
в PHP Я добавил:
putenv("NLS_LANG=AMERICAN_AMERICA.WE8ISO8859P1");
, чтобы соединение oci8 использовало этот набор символов.Получение é
с использованием oci8 из PHP теперь работает!(для varchars
, но не CLOBs
пришлось сделать utf8_encode
, чтобы извлечь его)
Итак, я попытался сохранить данные из PHP в Oracle ... и это не сработало ... где-то по пути из PHPдля Oracle é
становится ?
ОБНОВЛЕНИЕ: 9 марта в 14: 47
Итак, все ближе.После добавления переменной NLS_LANG выполнение прямой вставки oci8 с é
работает.
Проблема на самом деле на стороне PHP.Используя среду ExtJs, при отправке формы она кодирует ее с помощью encodeURIComponent
.
Так что é
отправляется как %C3%A9
, а затем перекодируется в é
.
Однако его длина теперь равна 2 (strlen($my_sent_value) = 2)
а не 1. А если в PHP я пытаюсь: $ my_sent_value == é
= FALSE
Я думаю, что смогу ли я перекодироватьВсе эти символы в PHP возвращаются к длине байта размером 1, а затем вставляя их в Oracle, это должно работать.
Все еще не повезло, хотя
ОБНОВЛЕНИЕ: 10 марта в 11: 05
Я продолжаю думать, что ятак близко (но так далеко).
putenv("NLS_LANG=AMERICAN_AMERICA.WE8ISO8859P9");
работает очень редко.
Я создал небольшой скрипт php для тестирования:
header('Content-Type: text/plain; charset=ISO-8859-1');
putenv("NLS_LANG=AMERICAN_AMERICA.WE8ISO8859P9");
$conn= oci_connect("user", "pass", "DB");
$stmt = oci_parse($conn, "UPDATE temp_tb SET string_field = '|é|'");
oci_execute($stmt, OCI_COMMIT_ON_SUCCESS);
После выполнения этого один раз и входа в базу данных Oracle напрямую я вижу, что STRING_FIELD установлен на |¿|
.Очевидно, это не то, что я ожидал от своего предыдущего опыта.
Однако, если я обновлю эту страницу PHP дважды быстро ... это сработало !!!
В Oracle я правильно увидел |é|
.
Может показаться, что переменная окружения неправильно установлена или отправлена вовремя для первого выполнения сценария, но доступна для второго выполнения.
Мой следующий эксперимент - экспортировать переменную в среду PHP, однако для этого мне нужно сбросить Apache ... так что посмотрим, что произойдет, надеюсь, это сработает.