-
Notifications
You must be signed in to change notification settings - Fork 345
Improve syntax violations interface #430
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
* New SyntaxViolation enum with description the same as prior strings * Replaced Fn signature in ParseOptions and Parser * Adapter for log_syntax_violation to be backward compatible * Improved ergonomics for use of closure, SyntaxViolation
Any chance I could get a review on this? @SimonSapin? |
Sorry for the delay. I haven’t looked at all the details yet but one thing I notice is that removing |
Thanks. I think I understand your point, in that removing The pendulum of concern for breaking changes seems to have swung fairly far from center with Rust libs in general of late. I think I may have just missed that memo. |
CC @nox, for opinions about SemVer |
Definitely a breaking change. |
You could do this instead: pub trait SyntaxViolationSink {
fn syntax_violation(&self, violation: SyntaxViolation);
}
impl SyntaxViolationSink for Fn(&'static str) {
fn syntax_violation(&self, violation: SyntaxViolation) {
self(violation.description())
}
} And then make the methods be: pub fn log_syntax_violation(self, new: Option<&'a Fn(&'static str)>) -> Self {
self.syntax_violation_callback(new)
}
pub fn syntax_violation_sink<F>(mut self, new: Option<&'a S>) -> Self
where
S: SyntaxViolationSink
{
…
} Btw @SimonSapin, why is this an |
Oh right silly me, if it were an |
And in my example of code, there is no reason to not use a trait object in pub fn syntax_violation_sink<F>(mut self, new: Option<&'a SyntaxViolationSink>) -> Self {
…
} |
And finally, |
Thanks @nox, very educational. I tried to convert from Regarding your last point. As part of this PR, I also changed Finally, I agree that this is breaking, for hypothetical edge cases, but does it require a major release? RFC 1105 seems to offer pragmatism, though this case isn't specifically addressed: https://github.com/rust-lang/rfcs/blob/master/text/1105-api-evolution.md
|
The question about There is a path to avoid the breaking change entirely, so it can definitely be a minor bump. As for making |
Thanks @nox and @SimonSapin. I did find a path forward, resubmitted as #433, which avoids these breaking changes. It doesn't allow for a simple closure wrapping old log Fn to a new callback, but it wasn't as bad as I originally imagined (and what led me to the |
Improve syntax violations interface and preserve Copy This is an alternative implementation of #430 which avoids introducing an `Rc<Fn>` and preserves `Copy` for `ParseOptions`. Thus, based on my current understanding with the prior review, it is completely backward compatible and with no breaking changes. Its a little less elegant in that, without the `Rc<Fn>`, I can not simple wrap the deprecated log_syntax_violation Fn with an adapting closure. But by moving the two possible function references into a new enum `ViolationFn` it is reasonably well contained. The interface for users is effectively the same, so I think the backward compatibility advantage makes this preferable to #430. Updated summary: ### Summary of changes This makes programmatic use of syntax violations more practical while further centralizing this concern in the parser, which should be a maintenance win. * New `SyntaxViolation` enum with descriptions the same as the prior violation static strings. This enables programmatic use of these violations by variant, e.g. ignoring some, warning on others, providing translated descriptions, etc. Enum implementation uses the same macro expansion pattern as was used for `ParseError`. * New `syntax_violation_callback` signature in `ParseOptions` and `Parser`. * Deprecated `log_syntax_violation` and re-implemented, passing the same violation descriptions for backward compatibility. * Unit tests for old `log_syntax_violation` compatibility, and new `syntax_violation_callback` * Includes rustdoc for old and new interfaces including tested example usage of new callback, as requested in #308. <!-- Reviewable:start --> --- This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/servo/rust-url/433) <!-- Reviewable:end -->
This makes programmatic use of syntax violations more practical while further centralizing this concern in the parser, which should be a maintenance win. An
Rc<Fn>
is introduced internally to satisfy borrow rules while improving ergonomics. The presumed minimal additional cost of this is only incurred if the syntax violation feature is used. Since existing public interface is maintained and changes are internal, I believe this meets requirements for backward compatibility, and testing agrees, but reviewers should definitely cover that aspect.Summary of changes
New
SyntaxViolation
enum with descriptions the same as the prior violation static strings. This enables programmatic use of these violations by variant, e.g. ignoring some, warning on others, etc. Enum implementation uses the same macro expansion pattern as was used forParseError
.New
syntax_violation_callback
signature inParseOptions
andParser
.Deprecated
log_syntax_violation
and re-implemented as adapter to new callback, passing the same violation descriptions for backward compatibility.Unit tests for old
log_syntax_violation
compatibility, and newsyntax_violation_callback
including a tested doc example.Includes rustdoc for old and new interfaces including example usage of new callback, as requested in Add examples to
ParseOptions
#308.Below items edited in light of discussion:
Improved ergonomics for
ParseOptions
andsyntax_violation_callback.
ParseOptions::parse
now takes &self, soParseOptions
can still be used repeatedly. The newsyntax_violation_callback
is passedFn
by value and can be passed inline in user code.Potential breaking changes:
ParseOptions
is no longerCopy
, andParseOptions::parse
takes&self
(wasself
, withCopy
).This change is