Code Monkey home page Code Monkey logo

Comments (24)

dennisdoomen avatar dennisdoomen commented on June 2, 2024

Sure, makes sense. What do you think @jnyrup ?

from fluentassertions.

jnyrup avatar jnyrup commented on June 2, 2024

It certainly makes sense to have more negated assertions for XML types 👍

You suggest adding an overload of NotHaveElement having an object unexpectedValue, but we don't currently have an affirmative HaveElement(string expectedElement, object expectedValue).
So I'm not sure we should add that overload.

We currently have HaveElement(string expectedName) on

  • XDocumentAssertions
  • XElementAssertions
  • XmlElementAssertions

and HaveAttribute(string expectedName, string expectedValue) on

  • XElementAssertions
  • XmlElementAssertions

In order to have a consistent API, it would be be nice to add the proposed methods on all relevant classes.

from fluentassertions.

skukshaus avatar skukshaus commented on June 2, 2024

Hey @jnyrup and @dennisdoomen

Thanks for the reply, should I implement the changes according to your guidelines and create another PR?
I mean, including the overloads for the other use cases as well.

(I mean, I really need this extension because I have a dirty workaround for my problem (I've added a Must<XElementAssertions>() method because Should<XElementAssertions>() is already there).)

BG Sergej

from fluentassertions.

dennisdoomen avatar dennisdoomen commented on June 2, 2024

Thanks for the reply, should I implement the changes according to your guidelines and create another PR?

Everything that is in this proposal should be delivered as a consistent set of changes. And to prevent contributors from abandoning the work after the first PR, we need to insist on contributors to provide a PR that covers everything that is needed to maintain that consistency. Hope you understand.

from fluentassertions.

dennisdoomen avatar dennisdoomen commented on June 2, 2024

It took me a couple of seconds to realize that element.Should().NotHaveElement("surname", "smith"); meant that element should not have an element with a specific value. I guess that also means that if element has element surname with a different value, it is okay? If so, then I think we should call it NotHaveElementWithValue.

In that case, we need:

  • XDocumentAssertions.HaveElementWithValue

  • XDocumentAssertions.NotHaveElementWithValue

  • XDocumentAssertions.NotHaveElement

  • XElementAssertions.HaveElementWithValue

  • XElementAssertions.NotHaveElementWithValue

  • XElementAssertions.NotHaveElement

  • XElementAssertions.HaveAttributeWithValue

  • XElementAssertions.NotHaveAttributeWithValue

  • XElementAssertions.NotHaveAttribute

To be clear, you can only add the NotHaveElementWithValue if you also include HaveElementWithValue

XmlElementAssertions are out of scope as far as I'm concerned.

from fluentassertions.

dennisdoomen avatar dennisdoomen commented on June 2, 2024

@jnyrup @skukshaus any thoughts?

from fluentassertions.

skukshaus avatar skukshaus commented on June 2, 2024

Sorry for the delay, Dennis,
I am a bit busy currently, so I was unable to complete the request at the moment.
BG Sergej

from fluentassertions.

jnyrup avatar jnyrup commented on June 2, 2024

We currently have XmlElementAssertions.HaveAttribute(string expectedName, string expectedValue) and XElementAssertions.HaveAttribute(string expectedName, string expectedValue).
In hindsight these should probably had been named HaveAttributeWithValue to distinguish them from asserting whether an element has an attribute with any value.

To avoid scope creeping, I suggest we focus on NotHaveElement for now to progress towards an API approval.

public class XDocumentAssertions
{
    public AndConstraint<XDocumentAssertions> NotHaveElement(string unexpected, string because = "", params object[] becauseArgs)
    public AndConstraint<XDocumentAssertions> NotHaveElement(XName unexpected, string because = "", params object[] becauseArgs)
}

public class XElementAssertions
{
    public AndConstraint<XElementAssertions> NotHaveElement(string unexpected, string because = "", params object[] becauseArgs)
    public AndConstraint<XElementAssertions> NotHaveElement(XName unexpected, string because = "", params object[] becauseArgs)
}

public class XmlElementAssertions
{
    public AndConstraint<XmlElementAssertions> NotHaveElement(string unexpectedName, string because = "", params object[] becauseArgs)
}

from fluentassertions.

dennisdoomen avatar dennisdoomen commented on June 2, 2024

I'd rather use this opportunity to correct the situation.

from fluentassertions.

leus avatar leus commented on June 2, 2024

Hey, I need this also - willing to help if you need an extra pair of hands.

from fluentassertions.

jnyrup avatar jnyrup commented on June 2, 2024

@leus as we're discussing several methods, which one(s) are you looking for?

from fluentassertions.

jnyrup avatar jnyrup commented on June 2, 2024

I'd rather use this opportunity to correct the situation.

Then I guess we should have:

  • HaveAttribute(string expectedName)
    • The attribute exists and can have any value
  • HaveAttributeWithValue(string expectedName, string expectedValue)
    • The attribute exists and has a particular value
  • NotHaveAttribute(string unexpectedName)
    • The attribute does not exist
  • NotHaveAttributeWithValue(string unexpectedName, string unexpectedValue)
    • The attribute either does not exists or doesn't have the particular value

from fluentassertions.

eNeRGy164 avatar eNeRGy164 commented on June 2, 2024

I think the last one is a bit ambiguous. I would opt for NotHaveAttributeValue and to require the attribute itself actually exist.
(Which would make HaveAttributeValue the opposite)

from fluentassertions.

dennisdoomen avatar dennisdoomen commented on June 2, 2024

I'd rather use this opportunity to correct the situation.

Then I guess we should have:

  • HaveAttribute(string expectedName)

    • The attribute exists and can have any value
  • HaveAttributeWithValue(string expectedName, string expectedValue)

    • The attribute exists and has a particular value
  • NotHaveAttribute(string unexpectedName)

    • The attribute does not exist
  • NotHaveAttributeWithValue(string unexpectedName, string unexpectedValue)

    • The attribute either does not exists or doesn't have the particular value

Yes, on XDocumentAssertions and XElementAssertions. I would skip XmlElementAssertions

I think the last one is a bit ambiguous. I would opt for NotHaveAttributeValue and to require the attribute itself actually exist.
(Which would make HaveAttributeValue the opposite)

ChatGPT believes that the behavior suggested by @jnyrup makes more sense. I tend to agree.

from fluentassertions.

dennisdoomen avatar dennisdoomen commented on June 2, 2024

Hey, I need this also - willing to help if you need an extra pair of hands.

@leus I'll ping you when we have settled on the API.

from fluentassertions.

leus avatar leus commented on June 2, 2024

Sure - in the meantime I'm using node.Element(something).Should().BeNull() (or something like that, I don'r remember) in my tests and it's not too bad but really bothers me. Looking forward to help.

from fluentassertions.

jnyrup avatar jnyrup commented on June 2, 2024

I think the last one is a bit ambiguous. I would opt for NotHaveAttributeValue and to require the attribute itself actually exist. (Which would make HaveAttributeValue the opposite)

If we let p be "having the attribute" and q "with the given value", then the negation is !(p && q) and by applying De Morgan's Law we !q || !p, or in prose "not having the attribute or not having the given value".

Asserting that some has an attribute but not with a given value would be HaveAttributeWithoutValue.

To avoid that confusion, we could e.g. choose to not expose either but let the developer write the unambigious:

foo.Should().HaveAttribute(bar)
    .Which.Value.Should().NotBe(baz);

I would skip XmlElementAssertions

Why?

from fluentassertions.

dennisdoomen avatar dennisdoomen commented on June 2, 2024

If we let p be "having the attribute" and q "with the given value", then the negation is !(p && q) and by applying De Morgan's Law we !q || !p, or in prose "not having the attribute or not having the given value".

Although I've learned something new again (thank you 😜), such formal definitions don't mean much for must developers. In the end it's about intuitivity.

To avoid that confusion, we could e.g. choose to not expose either but let the developer write the unambigious:

I like that.

Why?

To reduce the scope of this PR and because XmlElement are ancient. I haven't used those since we have XDocument.

from fluentassertions.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.