Estoy tratando de afirmar la igualdad de dos System.Drawing.Size
estructuras y obtengo una excepción de formato en lugar del error de afirmación esperado.
[TestMethod]
public void AssertStructs()
{
var struct1 = new Size(0, 0);
var struct2 = new Size(1, 1);
//This throws a format exception, "System.FormatException: Input string was not in a correct format."
Assert.AreEqual(struct1, struct2, "Failed. Expected {0}, actually it is {1}", struct1, struct2);
//This assert fails properly, "Failed. Expected {Width=0, Height=0}, actually it is {Width=1, Height=1}".
Assert.AreEqual(struct1, struct2, "Failed. Expected " + struct1 + ", actually it is " + struct2);
}
¿Es este comportamiento previsto? ¿Estoy haciendo algo mal aquí?
Assert.AreEqual(struct1, struct2, string.Format("Failed expected {0} actually is {1}
, struct1.ToString (), struct2.ToString ())) `?Respuestas:
Lo tengo. Y sí, es un error.
El problema es que hay dos niveles de
string.Format
acción aquí.El primer nivel de formateo es algo como:
Luego usamos
string.Format
con los parámetros que ha proporcionado:(Obviamente, se están proporcionando cultivos y algún tipo de desinfección ... pero no lo suficiente).
Eso se ve bien, a menos que los valores esperados y reales terminen con llaves, después de convertirse en una cadena, para lo cual sirven
Size
. Por ejemplo, su primer tamaño termina convirtiéndose en:Entonces, el segundo nivel de formato es algo como:
... y eso es lo que falla. Ay.
De hecho, podemos probar esto muy fácilmente engañando al formato para que use nuestros parámetros para las partes esperadas y reales:
El resultado es:
Claramente roto, ya que no lo esperábamos
foo
ni el valor realbar
.Básicamente, esto es como un ataque de inyección SQL, pero en el contexto bastante menos aterrador de
string.Format
.Como solución alternativa, puede utilizarlo
string.Format
como sugiere StriplingWarrior. Eso evita que se realice el segundo nivel de formateo en el resultado del formateo con los valores reales / esperados.fuente
%*n
equivalente? :(Creo que has encontrado un error.
Esto funciona (lanza una excepción de aserción):
Y esto funciona (genera el mensaje):
Pero esto no funciona (lanza un
FormatException
):No puedo pensar en ninguna razón por la que este comportamiento sería el esperado. Enviaría un informe de errores. Mientras tanto, aquí hay una solución:
fuente
Estoy de acuerdo con @StriplingWarrior en que esto parece ser un error con el método Assert.AreEqual () en al menos 2 sobrecargas. Como ya ha señalado StiplingWarrior, lo siguiente falla;
He estado experimentando un poco más sobre esto para ser un poco más explícito en el uso del código. Lo siguiente tampoco funciona;
Y
Esto me hizo pensar. System.Drawing.Size es una estructura. ¿Y los objetos? La lista parámetro no se especifica que la lista después de que el
string
mensaje esparams object[]
. Técnicamente, sí, las estructuras son objetos ... pero tipos especiales de objetos, es decir, tipos de valor. Creo que aquí es donde está el error. Si utilizamos nuestro propio objeto con un uso y estructura similares aSize
la siguiente realidad hace el trabajo;fuente
class
ostruct
, sino si elToString
valor contiene llaves que se parecen a unString.Format
.Creo que la primera afirmación es incorrecta.
Use esto en su lugar:
fuente