Update how TryFrom implementation are generated

… and remove TryFrom<Cow<'_, str>> implementations
This commit is contained in:
Jonas Platte 2020-05-30 19:28:06 +02:00
parent 5861457f3b
commit 7b30c2bb3e
No known key found for this signature in database
GPG Key ID: CC154DE0E30B7C67
7 changed files with 96 additions and 96 deletions

View File

@ -4,6 +4,10 @@ Breaking changes
* Removed diesel integration. If you were using it, please comment on the corresponding issue:
https://github.com/ruma/ruma-identifiers/issues/22
* Remove `TryFrom<Cow<'_, str>>` implementations for identifier types
* Update `parse_with_server_name`s signature (instead of `Into<String>` it now requires
`Into<Box<str>>` of the id type). This is technically a breaking change, but extremely unlikely
to affect any existing code.
# 0.16.1

View File

@ -1,6 +1,6 @@
//! Matrix event identifiers.
use std::{borrow::Cow, convert::TryFrom, num::NonZeroU8};
use std::num::NonZeroU8;
use crate::{error::Error, parse_id, validate_id};
@ -87,34 +87,32 @@ impl EventId {
}
}
impl TryFrom<Cow<'_, str>> for EventId {
type Error = Error;
/// Attempts to create a new Matrix event ID from a string representation.
///
/// If using the original event format as used by Matrix room versions 1 and 2, the string must
/// include the leading $ sigil, the localpart, a literal colon, and a valid homeserver
/// hostname.
fn try_from(event_id: Cow<'_, str>) -> Result<Self, Self::Error> {
if event_id.contains(':') {
let colon_idx = parse_id(&event_id, &['$'])?;
/// include the leading $ sigil, the localpart, a literal colon, and a valid homeserver hostname.
fn try_from<S>(event_id: S) -> Result<EventId, Error>
where
S: AsRef<str> + Into<Box<str>>,
{
if event_id.as_ref().contains(':') {
let colon_idx = parse_id(event_id.as_ref(), &['$'])?;
Ok(Self {
full_id: event_id.into_owned().into(),
Ok(EventId {
full_id: event_id.into(),
colon_idx: Some(colon_idx),
})
} else {
validate_id(&event_id, &['$'])?;
validate_id(event_id.as_ref(), &['$'])?;
Ok(Self {
full_id: event_id.into_owned().into(),
Ok(EventId {
full_id: event_id.into(),
colon_idx: None,
})
}
}
}
common_impls!(EventId, "a Matrix event ID");
common_impls!(EventId, try_from, "a Matrix event ID");
#[cfg(test)]
mod tests {

View File

@ -1,5 +1,5 @@
macro_rules! common_impls {
($id:ident, $desc:literal) => {
($id:ident, $try_from:ident, $desc:literal) => {
impl ::std::convert::From<$id> for ::std::string::String {
fn from(id: $id) -> Self {
id.full_id.into()
@ -10,7 +10,7 @@ macro_rules! common_impls {
type Error = crate::error::Error;
fn try_from(s: &str) -> Result<Self, Self::Error> {
Self::try_from(::std::borrow::Cow::Borrowed(s))
$try_from(s)
}
}
@ -18,7 +18,7 @@ macro_rules! common_impls {
type Error = crate::error::Error;
fn try_from(s: String) -> Result<Self, Self::Error> {
Self::try_from(::std::borrow::Cow::Owned(s))
$try_from(s)
}
}

View File

@ -1,6 +1,6 @@
//! Matrix room alias identifiers.
use std::{borrow::Cow, convert::TryFrom, num::NonZeroU8};
use std::num::NonZeroU8;
use crate::{error::Error, parse_id};
@ -35,23 +35,22 @@ impl RoomAliasId {
}
}
impl TryFrom<Cow<'_, str>> for RoomAliasId {
type Error = Error;
/// Attempts to create a new Matrix room alias ID from a string representation.
///
/// The string must include the leading # sigil, the alias, a literal colon, and a server name.
fn try_from(room_id: Cow<'_, str>) -> Result<Self, Error> {
let colon_idx = parse_id(&room_id, &['#'])?;
fn try_from<S>(room_id: S) -> Result<RoomAliasId, Error>
where
S: AsRef<str> + Into<Box<str>>,
{
let colon_idx = parse_id(room_id.as_ref(), &['#'])?;
Ok(Self {
full_id: room_id.into_owned().into(),
Ok(RoomAliasId {
full_id: room_id.into(),
colon_idx,
})
}
}
common_impls!(RoomAliasId, "a Matrix room alias ID");
common_impls!(RoomAliasId, try_from, "a Matrix room alias ID");
#[cfg(test)]
mod tests {

View File

@ -1,6 +1,6 @@
//! Matrix room identifiers.
use std::{borrow::Cow, convert::TryFrom, num::NonZeroU8};
use std::num::NonZeroU8;
use crate::{error::Error, parse_id};
@ -55,24 +55,22 @@ impl RoomId {
}
}
impl TryFrom<Cow<'_, str>> for RoomId {
type Error = Error;
/// Attempts to create a new Matrix room ID from a string representation.
///
/// The string must include the leading ! sigil, the localpart, a literal colon, and a server
/// name.
fn try_from(room_id: Cow<'_, str>) -> Result<Self, Error> {
let colon_idx = parse_id(&room_id, &['!'])?;
/// The string must include the leading ! sigil, the localpart, a literal colon, and a server name.
fn try_from<S>(room_id: S) -> Result<RoomId, Error>
where
S: AsRef<str> + Into<Box<str>>,
{
let colon_idx = parse_id(room_id.as_ref(), &['!'])?;
Ok(Self {
full_id: room_id.into_owned().into(),
Ok(RoomId {
full_id: room_id.into(),
colon_idx,
})
}
}
common_impls!(RoomId, "a Matrix room ID");
common_impls!(RoomId, try_from, "a Matrix room ID");
#[cfg(test)]
mod tests {

View File

@ -1,6 +1,6 @@
//! Matrix identifiers for places where a room ID or room alias ID are used interchangeably.
use std::{borrow::Cow, convert::TryFrom, hint::unreachable_unchecked, num::NonZeroU8};
use std::{convert::TryFrom, hint::unreachable_unchecked, num::NonZeroU8};
use crate::{error::Error, parse_id, RoomAliasId, RoomId};
@ -81,24 +81,27 @@ enum Variant {
RoomAliasId,
}
impl TryFrom<Cow<'_, str>> for RoomIdOrAliasId {
type Error = Error;
/// Attempts to create a new Matrix room ID or a room alias ID from a string representation.
///
/// The string must either include the leading ! sigil, the localpart, a literal colon, and a
/// valid homeserver host or include the leading # sigil, the alias, a literal colon, and a
/// valid homeserver host.
fn try_from(room_id_or_alias_id: Cow<'_, str>) -> Result<Self, Error> {
let colon_idx = parse_id(&room_id_or_alias_id, &['#', '!'])?;
Ok(Self {
full_id: room_id_or_alias_id.into_owned().into(),
fn try_from<S>(room_id_or_alias_id: S) -> Result<RoomIdOrAliasId, Error>
where
S: AsRef<str> + Into<Box<str>>,
{
let colon_idx = parse_id(room_id_or_alias_id.as_ref(), &['#', '!'])?;
Ok(RoomIdOrAliasId {
full_id: room_id_or_alias_id.into(),
colon_idx,
})
}
}
common_impls!(RoomIdOrAliasId, "a Matrix room ID or room alias ID");
common_impls!(
RoomIdOrAliasId,
try_from,
"a Matrix room ID or room alias ID"
);
impl From<RoomId> for RoomIdOrAliasId {
fn from(RoomId { full_id, colon_idx }: RoomId) -> Self {

View File

@ -1,6 +1,6 @@
//! Matrix user identifiers.
use std::{borrow::Cow, convert::TryFrom, num::NonZeroU8};
use std::num::NonZeroU8;
use crate::{error::Error, is_valid_server_name, parse_id};
@ -59,13 +59,13 @@ impl UserId {
/// localpart, not the localpart plus the `@` prefix, or the localpart plus server name without
/// the `@` prefix.
pub fn parse_with_server_name(
id: impl AsRef<str> + Into<String>,
id: impl AsRef<str> + Into<Box<str>>,
server_name: &str,
) -> Result<Self, Error> {
let id_str = id.as_ref();
if id_str.starts_with('@') {
Self::try_from(id.into())
try_from(id.into())
} else {
let is_fully_conforming = localpart_is_fully_comforming(id_str)?;
if !is_valid_server_name(server_name) {
@ -98,28 +98,26 @@ impl UserId {
}
}
impl TryFrom<Cow<'_, str>> for UserId {
type Error = Error;
/// Attempts to create a new Matrix user ID from a string representation.
///
/// The string must include the leading @ sigil, the localpart, a literal colon, and a server
/// name.
fn try_from(user_id: Cow<'_, str>) -> Result<Self, Error> {
let colon_idx = parse_id(&user_id, &['@'])?;
let localpart = &user_id[1..colon_idx.get() as usize];
/// The string must include the leading @ sigil, the localpart, a literal colon, and a server name.
fn try_from<S>(user_id: S) -> Result<UserId, Error>
where
S: AsRef<str> + Into<Box<str>>,
{
let colon_idx = parse_id(user_id.as_ref(), &['@'])?;
let localpart = &user_id.as_ref()[1..colon_idx.get() as usize];
let is_historical = localpart_is_fully_comforming(localpart)?;
Ok(Self {
full_id: user_id.into_owned().into(),
Ok(UserId {
full_id: user_id.into(),
colon_idx,
is_historical: !is_historical,
})
}
}
common_impls!(UserId, "a Matrix user ID");
common_impls!(UserId, try_from, "a Matrix user ID");
/// Check whether the given user id localpart is valid and fully conforming
///