route_tree 1.0.0-nullsafety copy "route_tree: ^1.0.0-nullsafety" to clipboard
route_tree: ^1.0.0-nullsafety copied to clipboard

outdated

A generic library for parsing URI paths.

RouteTree #

A generic library for parsing URI paths.

RouteTree is a generic routing library that makes it easy to implement routing logic based on the path segments of a URI. This is done by nesting [Segment] nodes to build a tree not unlike the [Widget] trees you see in Flutter apps.

Quick example #

final router = Segment.root<String>(
   create: (context) => "home",
   createError: (context) => "Error!",
   children: [
      Segment.path(
         name: "first_path",
         create: (context) => "routed to first_path",
      ),
      Segment.path(
         name: "second_path",
         create: (context) => "routed to second_path",
         children: [
         Segment.param(
            parser: const UintParser("id"),
            create: (context) => "routed to /second_path/${context["id"]}",
         ),
         ],
      ),
   ],
);

assert(router.route(Uri.parse("/second_path/12")), "routed to second_path/12");

Note the template parameter that denotes what data type [Segment.route] will return. This makes route_tree so flexible.

How it works #

The basic building blocks of this library are Segments, SegmentParsers and the ParseContext.

Segments #

Segments are to route_tree what Widgets are to Flutter. Each [Segment] represents a possible path segment that can be part of a route. Since it's templated it can be used in several ways, like routing in a Flutter app or choosing the correct function to handle incoming HTTP requests in a backend. The abstract class [Segment] contains several factory constructors to make finding the right one easier.

[RootSegment] or [Segment.root]

The root node of any route_tree.

Defines the "/"-route, the root error-handler as well as a list of [SegmentVerifier]s that can be used to assert certain properties of the route_tree.

By default RootSegments contain [findConflictingParamKeys], which returns an error if your route_tree contains duplicate parameter keys like /users/{id}/edit/{id}.

/// Matches "/"
final router = Segment.root<String>(
  create: (context) => "home",
  createError: (context) => "root error",
  children: [
    ...
  ],
);

[PathSegment] or [Segment.path]

The Segment you're probably gonna use most often. It defines a simple literal path segment. Internally children of a [Segment] with a [LiteralParser] (which by default only applies to [PathSegment]s) are contained in a Map<String, PathSegment> for constant time lookup of corresponding path segments.

Segment.root<String>(
  ...
  children: [
    /// Matches "/about"
    Segment.path(
      name: "about",
      create: (context) => "about",
    ),
    /// Matches "/settings/*", but not "/settings" itself, since [create] was
    /// left null
    Segment.path(
      name: "settings",
      children: [
        /// Matches "/settings/privacy"
        Segment.path(
          name: "privacy",
          create: (context) => "privacy",
        ),
      ],
    ),
  ],
);

[RegExpPathSegment] or [Segment.regExpPath]

Used to define one or (usually) more paths that should be matched by one [Segment] using a regular expression.

Segment.root<String>(
  ...
  children: [
    /// Matches any path segment consisting of letters
    Segment.regExpPath(
      regExp: RegExp(r"[a-zA-Z]+"),
      create: (context) => "letter path",
    ),
  ],
);

[ParamSegment] or [Segment.param]

Used to define a path parameter. If the segment of a URI is matched, the matched value is added to the [ParseContext], from which it can be queried using [ParseContext.operator[]]

Segment.root<String>(
  create: (context) => "home",
  createError: (context) => "error!",
  children: [
    /// Matches "/users/*", since [create] was left null
    Segment.path(
      name: "users",
      children: [
        /// Matches "/users/{id}", where {id} is any non-negative integer as defined
        /// by [UintParser].
        Segment.param(
          parser: const UintParser("id"),
          create: (context) => context["id"] as String,
        ),
      ],
    ),
  ],
);

[RegExpParamSegment] or [Segment.regExpParam]

Consider URLs used by Twitter where a URL like https://twitter.com/{name}, where name can be any word and a hypothetical Twitter client obviously couldn't hardcode all possible names. This is where this [Segment] comes into play. It can be used to define a path parameter that matches the provided regular expression and injects it into the [ParseContext], from which it can be queried using [ParseContext.operator[]].

final router = Segment.root<String>(
  create: (context) => "home",
  createError: (context) => "error!",
  children: [
    /// Matches any path segment consisting of letters
    Segment.regExpParam(
      parser: RegExpParamParser.forward(
        key: "name",
        regExp: RegExp(r"\w+"),
      ),
      create: (context) => context["name"] as String,
    ),
  ],
);

assert(router.route(Uri.parse("/flutterdev")) == "flutterdev");

SegmentParsers #

The actual parsing logic for looking up correct segments is delegated to instances of [SegmentParser]. The predefined parsers are:

  • [SegmentParser.withFunction], which takes a [Parser] function and can be used to quickly define custom SegmentParses
  • [LiteralParser], which is primarily used by [PathSegment] (& [Segment.path]) and matches a path segment literally
  • [RegExpParser], which matches a path segment against a regular expression
  • [ParamParser], subclass of [SegmentParser] and base class of parsers that inject matches into the [ParseContext]
  • [ParamParser.withFunction], which can be used to quickly define custom ParamParsers
  • [RegExpPararamParser], similar to [RegExpParser], but also injects a successful match into the [ParseContext]
  • [IntParser] & [UintParser], which match integers and non-negative integers respectively. The latter is useful for for id path parameters.

ParseContext #

The [ParseContext] holds the initial URI as well as any path parameters in the current route. It is passed to the create-function when they're called after a path has been matched.

1
likes
0
pub points
0%
popularity

Publisher

unverified uploader

A generic library for parsing URI paths.

Homepage
Repository (GitLab)
View/report issues

License

unknown (LICENSE)

Dependencies

result_class

More

Packages that depend on route_tree