def static( self, uri, file_or_directory: Union[str, bytes, PurePath], pattern=r"/?.+", use_modified_since=True, use_content_range=False, stream_large_files=False, name="static", host=None, strict_slashes=None, content_type=None, apply=True, ): """ Register a root to serve files from. The input can either be a file or a directory. This method will enable an easy and simple way to setup the :class:`Route` necessary to serve the static files. :param uri: URL path to be used for serving static content :param file_or_directory: Path for the Static file/directory with static files :param pattern: Regex Pattern identifying the valid static files :param use_modified_since: If true, send file modified time, and return not modified if the browser's matches the server's :param use_content_range: If true, process header for range requests and sends the file part that is requested :param stream_large_files: If true, use the :func:`StreamingHTTPResponse.file_stream` handler rather than the :func:`HTTPResponse.file` handler to send the file. If this is an integer, this represents the threshold size to switch to :func:`StreamingHTTPResponse.file_stream` :param name: user defined name used for url_for :param host: Host IP or FQDN for the service to use :param strict_slashes: Instruct :class:`Sanic` to check if the request URLs need to terminate with a */* :param content_type: user defined content type for header :return: routes registered on the router :rtype: List[sanic.router.Route] """ name = self._generate_name(name) if strict_slashes is None and self.strict_slashes is not None: strict_slashes = self.strict_slashes if not isinstance(file_or_directory, (str, bytes, PurePath)): raise ValueError( f"Static route must be a valid path, not {file_or_directory}") static = FutureStatic( uri, file_or_directory, pattern, use_modified_since, use_content_range, stream_large_files, name, host, strict_slashes, content_type, ) self._future_statics.add(static) if apply: self._apply_static(static)
def register(self, app, options): """ Register the blueprint to the sanic app. :param app: Instance of :class:`sanic.app.Sanic` class :param options: Options to be used while registering the blueprint into the app. *url_prefix* - URL Prefix to override the blueprint prefix """ self._apps.add(app) url_prefix = options.get("url_prefix", self.url_prefix) routes = [] middleware = [] exception_handlers = [] listeners = defaultdict(list) # Routes for future in self._future_routes: # attach the blueprint name to the handler so that it can be # prefixed properly in the router future.handler.__blueprintname__ = self.name # Prepend the blueprint URI prefix if available uri = url_prefix + future.uri if url_prefix else future.uri strict_slashes = ( self.strict_slashes if future.strict_slashes is None and self.strict_slashes is not None else future.strict_slashes ) name = app._generate_name(future.name) apply_route = FutureRoute( future.handler, uri[1:] if uri.startswith("//") else uri, future.methods, future.host or self.host, strict_slashes, future.stream, future.version or self.version, name, future.ignore_body, future.websocket, future.subprotocols, future.unquote, future.static, ) route = app._apply_route(apply_route) operation = ( routes.extend if isinstance(route, list) else routes.append ) operation(route) # Static Files for future in self._future_statics: # Prepend the blueprint URI prefix if available uri = url_prefix + future.uri if url_prefix else future.uri apply_route = FutureStatic(uri, *future[1:]) route = app._apply_static(apply_route) routes.append(route) route_names = [route.name for route in routes if route] # Middleware if route_names: for future in self._future_middleware: middleware.append(app._apply_middleware(future, route_names)) # Exceptions for future in self._future_exceptions: exception_handlers.append(app._apply_exception_handler(future)) # Event listeners for listener in self._future_listeners: listeners[listener.event].append(app._apply_listener(listener)) for signal in self._future_signals: signal.condition.update({"blueprint": self.name}) app._apply_signal(signal) self.routes = [route for route in routes if isinstance(route, Route)] # Deprecate these in 21.6 self.websocket_routes = [ route for route in self.routes if route.ctx.websocket ] self.middlewares = middleware self.exceptions = exception_handlers self.listeners = dict(listeners)
def register(self, app, options): """ Register the blueprint to the sanic app. :param app: Instance of :class:`sanic.app.Sanic` class :param options: Options to be used while registering the blueprint into the app. *url_prefix* - URL Prefix to override the blueprint prefix """ self._apps.add(app) url_prefix = options.get("url_prefix", self.url_prefix) opt_version = options.get("version", None) opt_strict_slashes = options.get("strict_slashes", None) opt_version_prefix = options.get("version_prefix", self.version_prefix) error_format = options.get("error_format", app.config.FALLBACK_ERROR_FORMAT) routes = [] middleware = [] exception_handlers = [] listeners = defaultdict(list) registered = set() # Routes for future in self._future_routes: # attach the blueprint name to the handler so that it can be # prefixed properly in the router future.handler.__blueprintname__ = self.name # Prepend the blueprint URI prefix if available uri = url_prefix + future.uri if url_prefix else future.uri version_prefix = self.version_prefix for prefix in ( future.version_prefix, opt_version_prefix, ): if prefix and prefix != "/v": version_prefix = prefix break version = self._extract_value(future.version, opt_version, self.version) strict_slashes = self._extract_value(future.strict_slashes, opt_strict_slashes, self.strict_slashes) name = app._generate_name(future.name) host = future.host or self.host if isinstance(host, list): host = tuple(host) apply_route = FutureRoute( future.handler, uri[1:] if uri.startswith("//") else uri, future.methods, host, strict_slashes, future.stream, version, name, future.ignore_body, future.websocket, future.subprotocols, future.unquote, future.static, version_prefix, error_format, future.route_context, ) if (self, apply_route) in app._future_registry: continue registered.add(apply_route) route = app._apply_route(apply_route) operation = (routes.extend if isinstance(route, list) else routes.append) operation(route) # Static Files for future in self._future_statics: # Prepend the blueprint URI prefix if available uri = url_prefix + future.uri if url_prefix else future.uri apply_route = FutureStatic(uri, *future[1:]) if (self, apply_route) in app._future_registry: continue registered.add(apply_route) route = app._apply_static(apply_route) routes.append(route) route_names = [route.name for route in routes if route] if route_names: # Middleware for future in self._future_middleware: if (self, future) in app._future_registry: continue middleware.append(app._apply_middleware(future, route_names)) # Exceptions for future in self._future_exceptions: if (self, future) in app._future_registry: continue exception_handlers.append( app._apply_exception_handler(future, route_names)) # Event listeners for future in self._future_listeners: if (self, future) in app._future_registry: continue listeners[future.event].append(app._apply_listener(future)) # Signals for future in self._future_signals: if (self, future) in app._future_registry: continue future.condition.update({"__blueprint__": self.name}) # Force exclusive to be False app._apply_signal(tuple((*future[:-1], False))) self.routes += [route for route in routes if isinstance(route, Route)] self.websocket_routes += [ route for route in self.routes if route.ctx.websocket ] self.middlewares += middleware self.exceptions += exception_handlers self.listeners.update(dict(listeners)) if self.registered: self.register_futures( self.apps, self, chain( registered, self._future_middleware, self._future_exceptions, self._future_listeners, self._future_signals, ), )