mirror of
https://github.com/silverstripe/silverstripe-framework
synced 2024-10-22 12:05:37 +00:00
ENHANCEMENT Introduce Database::prepStringForDB(), used by
DBField::prepValueForDB() and StringField::prepValueForDB() to ensure the field value is escaped correctly for the database. This means databases like MSSQL can introduce an "N" prefix (marking text as unicode to be saved correctly) by overloading the prepStringForDB method. MySQL, PostgreSQL and SQLite3 operate as usual.
This commit is contained in:
parent
fea3a4eea0
commit
02c8019bb8
@ -757,7 +757,19 @@ abstract class SS_Database {
|
|||||||
}
|
}
|
||||||
return $text;
|
return $text;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wrap a string into DB-specific quotes. MySQL, PostgreSQL and SQLite3 only need single quotes around the string.
|
||||||
|
* MSSQL will overload this and include it's own N prefix to mark the string as unicode, so characters like macrons
|
||||||
|
* are saved correctly.
|
||||||
|
*
|
||||||
|
* @param string $string String to be prepared for database query
|
||||||
|
* @return string Prepared string
|
||||||
|
*/
|
||||||
|
public function prepStringForDB($string) {
|
||||||
|
return "'" . Convert::raw2sql($string) . "'";
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function to return an SQL datetime expression that can be used with the adapter in use
|
* Function to return an SQL datetime expression that can be used with the adapter in use
|
||||||
* used for querying a datetime in a certain format
|
* used for querying a datetime in a certain format
|
||||||
|
@ -143,9 +143,9 @@ abstract class DBField extends ViewableData {
|
|||||||
if($value === null || $value === "" || $value === false) {
|
if($value === null || $value === "" || $value === false) {
|
||||||
return "null";
|
return "null";
|
||||||
} else {
|
} else {
|
||||||
return "'" . Convert::raw2sql($value) . "'";
|
return DB::getConn()->prepStringForDB($value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Prepare the current field for usage in a
|
* Prepare the current field for usage in a
|
||||||
|
@ -75,8 +75,8 @@ abstract class StringField extends DBField {
|
|||||||
* @see core/model/fieldtypes/DBField#prepValueForDB($value)
|
* @see core/model/fieldtypes/DBField#prepValueForDB($value)
|
||||||
*/
|
*/
|
||||||
function prepValueForDB($value) {
|
function prepValueForDB($value) {
|
||||||
if ( !$this->nullifyEmpty && $value === '' ) {
|
if(!$this->nullifyEmpty && $value === '') {
|
||||||
return "'" . Convert::raw2sql($value) . "'";
|
return DB::getConn()->prepStringForDB($value);
|
||||||
} else {
|
} else {
|
||||||
return parent::prepValueForDB($value);
|
return parent::prepValueForDB($value);
|
||||||
}
|
}
|
||||||
|
@ -22,7 +22,8 @@ class DBFieldTest extends SapphireTest {
|
|||||||
* Test the prepValueForDB() method on DBField.
|
* Test the prepValueForDB() method on DBField.
|
||||||
*/
|
*/
|
||||||
function testPrepValueForDB() {
|
function testPrepValueForDB() {
|
||||||
|
$db = DB::getConn();
|
||||||
|
|
||||||
/* Float behaviour, asserting we have 0 */
|
/* Float behaviour, asserting we have 0 */
|
||||||
$this->assertEquals('0', singleton('Float')->prepValueForDB(0));
|
$this->assertEquals('0', singleton('Float')->prepValueForDB(0));
|
||||||
$this->assertEquals('0', singleton('Float')->prepValueForDB(null));
|
$this->assertEquals('0', singleton('Float')->prepValueForDB(null));
|
||||||
@ -74,63 +75,64 @@ class DBFieldTest extends SapphireTest {
|
|||||||
$this->assertEquals("'1'", singleton('Boolean')->prepValueForDB('1'));
|
$this->assertEquals("'1'", singleton('Boolean')->prepValueForDB('1'));
|
||||||
|
|
||||||
/* Varchar behaviour */
|
/* Varchar behaviour */
|
||||||
|
$this->assertEquals($db->prepStringForDB("0"), singleton('Varchar')->prepValueForDB(0));
|
||||||
$this->assertEquals("'0'", singleton('Varchar')->prepValueForDB(0));
|
$this->assertEquals("'0'", singleton('Varchar')->prepValueForDB(0));
|
||||||
$this->assertEquals("null", singleton('Varchar')->prepValueForDB(null));
|
$this->assertEquals("null", singleton('Varchar')->prepValueForDB(null));
|
||||||
$this->assertEquals("null", singleton('Varchar')->prepValueForDB(false));
|
$this->assertEquals("null", singleton('Varchar')->prepValueForDB(false));
|
||||||
$this->assertEquals("null", singleton('Varchar')->prepValueForDB(''));
|
$this->assertEquals("null", singleton('Varchar')->prepValueForDB(''));
|
||||||
$this->assertEquals("'0'", singleton('Varchar')->prepValueForDB('0'));
|
$this->assertEquals($db->prepStringForDB("0"), singleton('Varchar')->prepValueForDB('0'));
|
||||||
$this->assertEquals("'1'", singleton('Varchar')->prepValueForDB(1));
|
$this->assertEquals($db->prepStringForDB("1"), singleton('Varchar')->prepValueForDB(1));
|
||||||
$this->assertEquals("'1'", singleton('Varchar')->prepValueForDB(true));
|
$this->assertEquals($db->prepStringForDB("1"), singleton('Varchar')->prepValueForDB(true));
|
||||||
$this->assertEquals("'1'", singleton('Varchar')->prepValueForDB('1'));
|
$this->assertEquals($db->prepStringForDB("1"), singleton('Varchar')->prepValueForDB('1'));
|
||||||
$this->assertEquals("'00000'", singleton('Varchar')->prepValueForDB('00000'));
|
$this->assertEquals($db->prepStringForDB("00000"), singleton('Varchar')->prepValueForDB('00000'));
|
||||||
$this->assertEquals("'0'", singleton('Varchar')->prepValueForDB(0000));
|
$this->assertEquals($db->prepStringForDB("0"), singleton('Varchar')->prepValueForDB(0000));
|
||||||
$this->assertEquals("'test'", singleton('Varchar')->prepValueForDB('test'));
|
$this->assertEquals($db->prepStringForDB("test"), singleton('Varchar')->prepValueForDB('test'));
|
||||||
$this->assertEquals("'123'", singleton('Varchar')->prepValueForDB(123));
|
$this->assertEquals($db->prepStringForDB("123"), singleton('Varchar')->prepValueForDB(123));
|
||||||
|
|
||||||
/* AllowEmpty Varchar behaviour */
|
/* AllowEmpty Varchar behaviour */
|
||||||
$varcharField = new Varchar("testfield", 50, array("nullifyEmpty"=>false));
|
$varcharField = new Varchar("testfield", 50, array("nullifyEmpty"=>false));
|
||||||
$this->assertSame("'0'", $varcharField->prepValueForDB(0));
|
$this->assertSame($db->prepStringForDB("0"), $varcharField->prepValueForDB(0));
|
||||||
$this->assertSame("null", $varcharField->prepValueForDB(null));
|
$this->assertSame("null", $varcharField->prepValueForDB(null));
|
||||||
$this->assertSame("null", $varcharField->prepValueForDB(false));
|
$this->assertSame("null", $varcharField->prepValueForDB(false));
|
||||||
$this->assertSame("''", $varcharField->prepValueForDB(''));
|
$this->assertSame($db->prepStringForDB(""), $varcharField->prepValueForDB(''));
|
||||||
$this->assertSame("'0'", $varcharField->prepValueForDB('0'));
|
$this->assertSame($db->prepStringForDB("0"), $varcharField->prepValueForDB('0'));
|
||||||
$this->assertSame("'1'", $varcharField->prepValueForDB(1));
|
$this->assertSame($db->prepStringForDB("1"), $varcharField->prepValueForDB(1));
|
||||||
$this->assertSame("'1'", $varcharField->prepValueForDB(true));
|
$this->assertSame($db->prepStringForDB("1"), $varcharField->prepValueForDB(true));
|
||||||
$this->assertSame("'1'", $varcharField->prepValueForDB('1'));
|
$this->assertSame($db->prepStringForDB("1"), $varcharField->prepValueForDB('1'));
|
||||||
$this->assertSame("'00000'", $varcharField->prepValueForDB('00000'));
|
$this->assertSame($db->prepStringForDB("00000"), $varcharField->prepValueForDB('00000'));
|
||||||
$this->assertSame("'0'", $varcharField->prepValueForDB(0000));
|
$this->assertSame($db->prepStringForDB("0"), $varcharField->prepValueForDB(0000));
|
||||||
$this->assertSame("'test'", $varcharField->prepValueForDB('test'));
|
$this->assertSame($db->prepStringForDB("test"), $varcharField->prepValueForDB('test'));
|
||||||
$this->assertSame("'123'", $varcharField->prepValueForDB(123));
|
$this->assertSame($db->prepStringForDB("123"), $varcharField->prepValueForDB(123));
|
||||||
unset($varcharField);
|
unset($varcharField);
|
||||||
|
|
||||||
/* Text behaviour */
|
/* Text behaviour */
|
||||||
$this->assertEquals("'0'", singleton('Text')->prepValueForDB(0));
|
$this->assertEquals($db->prepStringForDB("0"), singleton('Text')->prepValueForDB(0));
|
||||||
$this->assertEquals("null", singleton('Text')->prepValueForDB(null));
|
$this->assertEquals("null", singleton('Text')->prepValueForDB(null));
|
||||||
$this->assertEquals("null", singleton('Text')->prepValueForDB(false));
|
$this->assertEquals("null", singleton('Text')->prepValueForDB(false));
|
||||||
$this->assertEquals("null", singleton('Text')->prepValueForDB(''));
|
$this->assertEquals("null", singleton('Text')->prepValueForDB(''));
|
||||||
$this->assertEquals("'0'", singleton('Text')->prepValueForDB('0'));
|
$this->assertEquals($db->prepStringForDB("0"), singleton('Text')->prepValueForDB('0'));
|
||||||
$this->assertEquals("'1'", singleton('Text')->prepValueForDB(1));
|
$this->assertEquals($db->prepStringForDB("1"), singleton('Text')->prepValueForDB(1));
|
||||||
$this->assertEquals("'1'", singleton('Text')->prepValueForDB(true));
|
$this->assertEquals($db->prepStringForDB("1"), singleton('Text')->prepValueForDB(true));
|
||||||
$this->assertEquals("'1'", singleton('Text')->prepValueForDB('1'));
|
$this->assertEquals($db->prepStringForDB("1"), singleton('Text')->prepValueForDB('1'));
|
||||||
$this->assertEquals("'00000'", singleton('Text')->prepValueForDB('00000'));
|
$this->assertEquals($db->prepStringForDB("00000"), singleton('Text')->prepValueForDB('00000'));
|
||||||
$this->assertEquals("'0'", singleton('Text')->prepValueForDB(0000));
|
$this->assertEquals($db->prepStringForDB("0"), singleton('Text')->prepValueForDB(0000));
|
||||||
$this->assertEquals("'test'", singleton('Text')->prepValueForDB('test'));
|
$this->assertEquals($db->prepStringForDB("test"), singleton('Text')->prepValueForDB('test'));
|
||||||
$this->assertEquals("'123'", singleton('Text')->prepValueForDB(123));
|
$this->assertEquals($db->prepStringForDB("123"), singleton('Text')->prepValueForDB(123));
|
||||||
|
|
||||||
/* AllowEmpty Text behaviour */
|
/* AllowEmpty Text behaviour */
|
||||||
$textField = new Text("testfield", array("nullifyEmpty"=>false));
|
$textField = new Text("testfield", array("nullifyEmpty"=>false));
|
||||||
$this->assertSame("'0'", $textField->prepValueForDB(0));
|
$this->assertSame($db->prepStringForDB("0"), $textField->prepValueForDB(0));
|
||||||
$this->assertSame("null", $textField->prepValueForDB(null));
|
$this->assertSame("null", $textField->prepValueForDB(null));
|
||||||
$this->assertSame("null", $textField->prepValueForDB(false));
|
$this->assertSame("null", $textField->prepValueForDB(false));
|
||||||
$this->assertSame("''", $textField->prepValueForDB(''));
|
$this->assertSame($db->prepStringForDB(""), $textField->prepValueForDB(''));
|
||||||
$this->assertSame("'0'", $textField->prepValueForDB('0'));
|
$this->assertSame($db->prepStringForDB("0"), $textField->prepValueForDB('0'));
|
||||||
$this->assertSame("'1'", $textField->prepValueForDB(1));
|
$this->assertSame($db->prepStringForDB("1"), $textField->prepValueForDB(1));
|
||||||
$this->assertSame("'1'", $textField->prepValueForDB(true));
|
$this->assertSame($db->prepStringForDB("1"), $textField->prepValueForDB(true));
|
||||||
$this->assertSame("'1'", $textField->prepValueForDB('1'));
|
$this->assertSame($db->prepStringForDB("1"), $textField->prepValueForDB('1'));
|
||||||
$this->assertSame("'00000'", $textField->prepValueForDB('00000'));
|
$this->assertSame($db->prepStringForDB("00000"), $textField->prepValueForDB('00000'));
|
||||||
$this->assertSame("'0'", $textField->prepValueForDB(0000));
|
$this->assertSame($db->prepStringForDB("0"), $textField->prepValueForDB(0000));
|
||||||
$this->assertSame("'test'", $textField->prepValueForDB('test'));
|
$this->assertSame($db->prepStringForDB("test"), $textField->prepValueForDB('test'));
|
||||||
$this->assertSame("'123'", $textField->prepValueForDB(123));
|
$this->assertSame($db->prepStringForDB("123"), $textField->prepValueForDB(123));
|
||||||
unset($textField);
|
unset($textField);
|
||||||
|
|
||||||
/* Time behaviour */
|
/* Time behaviour */
|
||||||
|
Loading…
x
Reference in New Issue
Block a user