def find(path=None):
        if path is None:
            folders = set()
            for blueprint in app.blueprints.values():
                if blueprint.static_folder is not None:
                    folders.update([blueprint.static_folder])
            folders.update([app.static_folder])
            return folders
        else:
            for rule in app.url_map.iter_rules():
                if '.' in rule.endpoint:
                    with_blueprint = True
                    blueprint_name = rule.endpoint.rsplit('.', 1)[0]
                    if blueprint_name not in app.blueprints:
                        continue
                    blueprint = app.blueprints[blueprint_name]

                    data = rule.match(u('{subdomain}|{path}').format(
                        subdomain=blueprint.subdomain or '',
                        path=path,
                    ))
                else:
                    with_blueprint = False
                    data = rule.match(u('|{0}').format(path))

                if data:
                    static_folder = blueprint.static_folder \
                        if with_blueprint and blueprint.static_folder is not None \
                        else app.static_folder
                    return os.path.join(static_folder, data['filename'])

        raise IOError(2, u('File not found {0}.').format(path))
Example #2
0
    def find(path=None):
        if path is None:
            folders = set()
            for blueprint in app.blueprints.values():
                if blueprint.static_folder is not None:
                    folders.update([blueprint.static_folder])
            folders.update([app.static_folder])
            return folders
        else:
            for rule in app.url_map.iter_rules():
                if '.' in rule.endpoint:
                    with_blueprint = True
                    blueprint_name = rule.endpoint.rsplit('.', 1)[0]
                    if blueprint_name not in app.blueprints:
                        continue
                    blueprint = app.blueprints[blueprint_name]

                    data = rule.match(
                        u('{subdomain}|{path}').format(
                            subdomain=blueprint.subdomain or '',
                            path=path,
                        ))
                else:
                    with_blueprint = False
                    data = rule.match(u('|{0}').format(path))

                if data:
                    static_folder = blueprint.static_folder \
                        if with_blueprint and blueprint.static_folder is not None \
                        else app.static_folder
                    return os.path.join(static_folder, data['filename'])

        raise IOError(2, u('File not found {0}.').format(path))
Example #3
0
 def render_element(self, filename, type):
     """Returns an html element pointing to filename as a string.
     """
     if type.lower() == 'css':
         return u('<link type="text/css" rel="stylesheet" href="{0}" />').format(filename)
     elif type.lower() == 'js':
         return u('<script type="text/javascript" src="{0}"></script>').format(filename)
     else:
         raise RuntimeError(u('Unsupported type of compression {0}').format(type))
Example #4
0
 def _display_block(self, compression_type, caller):
     html = caller()
     html_hash = self.compressor.make_hash(html)
     filename = os.path.join(u('{hash}.{extension}').format(
         hash=html_hash,
         extension=compression_type,
     ))
     static_prefix = u(self.compressor.config.compressor_static_prefix)
     return self.compressor.render_element(os.path.join(static_prefix, filename), compression_type)
Example #5
0
 def render_element(self, filename, type):
     """Returns an html element pointing to filename as a string.
     """
     if type.lower() == 'css':
         return u('<link type="text/css" rel="stylesheet" href="{0}" />'
                  ).format(filename)
     elif type.lower() == 'js':
         return u('<script type="text/javascript" src="{0}"></script>'
                  ).format(filename)
     else:
         raise RuntimeError(
             u('Unsupported type of compression {0}').format(type))
Example #6
0
    def compile(cls,
                what,
                mimetype='text/less',
                cwd=None,
                uri_cwd=None,
                debug=None):
        args = []

        if not debug:
            args += ['--compress']

        if cwd:
            args += ['-ru']
            args += ['--include-path={}'.format(cwd)]

        if uri_cwd:
            if not uri_cwd.endswith('/'):
                uri_cwd += '/'
            args += ['--rootpath={}'.format(uri_cwd)]

        if cls.extra_args:
            args.extend(cls.extra_args)

        args += ['-']

        args.insert(0, cls.binary)

        try:
            handler = subprocess.Popen(args,
                                       stdout=subprocess.PIPE,
                                       stdin=subprocess.PIPE,
                                       stderr=subprocess.PIPE,
                                       cwd=None)
        except OSError as e:
            msg = '{0} encountered an error when executing {1}: {2}'.format(
                cls.__name__,
                cls.binary,
                u(e),
            )
            if e.errno == errno.ENOENT:
                msg += ' Make sure {0} is in your PATH.'.format(cls.binary)
            raise InvalidCompressorError(msg)

        if isinstance(what, file):
            what = what.read()
        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError('Test this :S %s' % stderr)
Example #7
0
    def compile(cls, what, mimetype='text/less', cwd=None, uri_cwd=None,
                debug=None):
        args = ['lessc']

        if not debug:
            args += ['--compress']

        if cwd:
            args += ['-ru']
            args += ['--include-path={}'.format(cwd)]

        if uri_cwd:
            if not uri_cwd.endswith('/'):
                uri_cwd += '/'
            args += ['--rootpath={}'.format(uri_cwd)]

        args += ['-']

        handler = subprocess.Popen(args,
                                   stdout=subprocess.PIPE,
                                   stdin=subprocess.PIPE,
                                   stderr=subprocess.PIPE, cwd=None)

        if isinstance(what, file):
            what = what.read()
        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError('Test this :S %s' % stderr)
Example #8
0
    def compile(cls,
                what,
                mimetype='text/sass',
                cwd=None,
                uri_cwd=None,
                debug=None):
        args = ['sass', '-s']
        if mimetype == 'text/scss':
            args.append('--scss')

        if cwd:
            args += ['-I', cwd]

        handler = subprocess.Popen(args,
                                   stdout=subprocess.PIPE,
                                   stdin=subprocess.PIPE,
                                   stderr=subprocess.PIPE,
                                   cwd=None)

        if isinstance(what, file):
            what = what.read()
        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError('Test this :S %s' % stderr)
Example #9
0
    def compile(cls, what, mimetype='text/less', cwd=None, uri_cwd=None,
                debug=None):
        args = ['lessc']

        if not debug:
            args += ['--compress']

        if cwd:
            args += ['-ru']
            args += ['--include-path={}'.format(cwd)]

        if uri_cwd:
            if not uri_cwd.endswith('/'):
                uri_cwd += '/'
            args += ['--rootpath={}'.format(uri_cwd)]

        args += ['-']

        handler = subprocess.Popen(args,
                                   stdout=subprocess.PIPE,
                                   stdin=subprocess.PIPE,
                                   stderr=subprocess.PIPE, cwd=None)

        if isinstance(what, file):
            what = what.read()
        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError('Test this :S %s' % stderr)
    def compile(cls,
                what,
                mimetype='text/coffeescript',
                cwd=None,
                uri_cwd=None,
                debug=None):

        args = ['coffee', '--compile', '--stdio']

        handler = subprocess.Popen(args,
                                   stdout=subprocess.PIPE,
                                   stdin=subprocess.PIPE,
                                   stderr=subprocess.PIPE,
                                   cwd=None)

        if isinstance(what, file):
            what = what.read()

        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if not debug:
            stdout = jsmin(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError('Test this :S %s' % stderr)
    def compile(cls, what, mimetype='text/less', cwd=None, uri_cwd=None,
                debug=None):
        args = []

        if not debug:
            args += ['--compress']

        if cwd:
            args += ['-ru']
            args += ['--include-path={}'.format(cwd)]

        if uri_cwd:
            if not uri_cwd.endswith('/'):
                uri_cwd += '/'
            args += ['--rootpath={}'.format(uri_cwd)]

        if cls.extra_args:
            args.extend(cls.extra_args)

        args += ['-']

        args.insert(0, cls.binary)

        try:
            handler = subprocess.Popen(args,
                                       stdout=subprocess.PIPE,
                                       stdin=subprocess.PIPE,
                                       stderr=subprocess.PIPE, cwd=None)
        except OSError as e:
            msg = '{0} encountered an error when executing {1}: {2}'.format(
                cls.__name__,
                cls.binary,
                u(e),
            )
            if e.errno == errno.ENOENT:
                msg += ' Make sure {0} is in your PATH.'.format(cls.binary)
            raise InvalidCompressorError(msg)

        if isinstance(what, file):
            what = what.read()
        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError('Test this :S %s' % stderr)
Example #12
0
    def find_compilable_tags(self, soup):
        tags = ['link', 'style', 'script']
        for tag in soup.find_all(tags):

            # don't compress externally hosted assets
            src = tag.get('src') or tag.get('href')
            if src and (src.startswith('http') or src.startswith('//')):
                continue

            if tag.get('type') is None:
                if tag.name == 'script':
                    tag['type'] = 'text/javascript'
                if tag.name == 'style':
                    tag['type'] = 'text/css'
            else:
                tag['type'] == tag['type'].lower()

            if tag.get('type') is None:
                raise RuntimeError(
                    u('Tags to be compressed must have a type attribute: {0}').
                    format(u(tag)))

            yield tag
Example #13
0
    def find_file(self, path):
        if callable(self.config.compressor_source_dirs):
            filename = self.config.compressor_source_dirs(path)
            if os.path.exists(filename):
                return filename
        else:
            if isinstance(self.config.compressor_source_dirs, basestring):
                dirs = [self.config.compressor_source_dirs]
            else:
                dirs = self.config.compressor_source_dirs

            for d in dirs:
                if self.config.compressor_static_prefix_precompress is not None and path.startswith('/'):
                    path = path.replace(self.config.compressor_static_prefix_precompress, '', 1).lstrip(os.sep).lstrip('/')
                filename = os.path.join(d, path)
                if os.path.exists(filename):
                    return filename

        raise IOError(2, u('File not found {0}').format(path))
Example #14
0
    def find_compilable_tags(self, soup):
        tags = ['link', 'style', 'script']
        for tag in soup.find_all(tags):

            # don't compress externally hosted assets
            src = tag.get('src') or tag.get('href')
            if src and (src.startswith('http') or src.startswith('//')):
                continue

            if tag.get('type') is None:
                if tag.name == 'script':
                    tag['type'] = 'text/javascript'
                if tag.name == 'style':
                    tag['type'] = 'text/css'
            else:
                tag['type'] == tag['type'].lower()

            if tag.get('type') is None:
                raise RuntimeError(u('Tags to be compressed must have a type attribute: {0}').format(u(tag)))

            yield tag
    def compile(cls, what, mimetype="text/coffeescript", cwd=None, uri_cwd=None, debug=None):

        args = ["coffee", "--compile", "--stdio"]

        handler = subprocess.Popen(
            args, stdout=subprocess.PIPE, stdin=subprocess.PIPE, stderr=subprocess.PIPE, cwd=None
        )

        if isinstance(what, file):
            what = what.read()

        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if not debug:
            stdout = jsmin(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError("Test this :S %s" % stderr)
Example #16
0
    def find_file(self, path):
        if callable(self.config.compressor_source_dirs):
            filename = self.config.compressor_source_dirs(path)
            if os.path.exists(filename):
                return filename
        else:
            if isinstance(self.config.compressor_source_dirs, basestring):
                dirs = [self.config.compressor_source_dirs]
            else:
                dirs = self.config.compressor_source_dirs

            for d in dirs:
                if self.config.compressor_static_prefix_precompress is not None and path.startswith(
                        '/'):
                    path = path.replace(self.config.compressor_static_prefix_precompress, '', 1).\
                        lstrip(os.sep).lstrip('/')
                filename = os.path.join(d, path)
                if os.path.exists(filename):
                    return filename

        raise IOError(2, u('File not found {0}').format(path))
Example #17
0
    def compile(cls, what, mimetype='text/sass', cwd=None,
                uri_cwd=None, debug=None):
        args = ['sass', '-s']
        if mimetype == 'text/scss':
            args.append('--scss')

        if cwd:
            args += ['-I', cwd]

        handler = subprocess.Popen(args,
                                   stdout=subprocess.PIPE,
                                   stdin=subprocess.PIPE,
                                   stderr=subprocess.PIPE, cwd=None)

        if isinstance(what, file):
            what = what.read()
        (stdout, stderr) = handler.communicate(input=utf8_encode(what))
        stdout = u(stdout)

        if handler.returncode == 0:
            return stdout
        else:
            raise RuntimeError('Test this :S %s' % stderr)
Example #18
0
    def compress(self, html, compression_type):

        if not self.config.compressor_enabled:
            return html

        compression_type = compression_type.lower()
        html_hash = self.make_hash(html)

        if not os.path.exists(u(self.config.compressor_output_dir)):
            os.makedirs(u(self.config.compressor_output_dir))

        cached_file = os.path.join(
            u(self.config.compressor_output_dir),
            u('{hash}.{extension}').format(
                hash=html_hash,
                extension=compression_type,
            ),
        )

        if os.path.exists(cached_file):
            filename = os.path.join(
                u(self.config.compressor_static_prefix),
                os.path.basename(cached_file),
            )
            return self.render_element(filename, compression_type)

        assets = OrderedDict()
        soup = BeautifulSoup(html, PARSER)
        for count, c in enumerate(self.find_compilable_tags(soup)):

            url = c.get('src') or c.get('href')
            if url:
                filename = os.path.basename(u(url)).split('.', 1)[0]
                uri_cwd = os.path.join(u(self.config.compressor_static_prefix), os.path.dirname(u(url)))
                text = open(self.find_file(u(url)), 'r', encoding='utf-8')
                cwd = os.path.dirname(text.name)
            else:
                filename = u('inline{0}').format(count)
                uri_cwd = None
                text = c.string
                cwd = None

            mimetype = c['type'].lower()
            try:
                compressor = self.config.compressor_classes[mimetype]
            except KeyError:
                msg = u('Unsupported type of compression {0}').format(mimetype)
                raise RuntimeError(msg)

            text = self.get_contents(text)
            compressed = compressor.compile(text,
                                            mimetype=mimetype,
                                            cwd=cwd,
                                            uri_cwd=uri_cwd,
                                            debug=self.config.compressor_debug)

            if not self.config.compressor_debug:
                outfile = cached_file
            else:
                outfile = os.path.join(
                    u(self.config.compressor_output_dir),
                    u('{hash}-{filename}.{extension}').format(
                        hash=html_hash,
                        filename=filename,
                        extension=compression_type,
                    ),
                )

            if assets.get(outfile) is None:
                assets[outfile] = u('')
            assets[outfile] += u("\n") + compressed

        blocks = u('')
        for outfile, asset in assets.items():
            with open(outfile, 'w', encoding='utf-8') as fh:
                fh.write(asset)
            filename = os.path.join(
                u(self.config.compressor_static_prefix),
                os.path.basename(outfile),
            )
            blocks += self.render_element(filename, compression_type)

        return blocks
Example #19
0
 def get_contents(self, src):
     if isinstance(src, file):
         return u(src.read())
     else:
         return u(src)
Example #20
0
 def get_contents(self, src):
     if isinstance(src, file):
         return u(src.read())
     else:
         return u(src)
 def _display_block(self, compression_type, caller):
     html = caller()
     html_hash = self.compressor.make_hash(html)
     filename = os.path.join(u("{hash}.{extension}").format(hash=html_hash, extension=compression_type))
     static_prefix = u(self.compressor.config.compressor_static_prefix)
     return self.compressor.render_element(os.path.join(static_prefix, filename), compression_type)
Example #22
0
    def compress(self, html, compression_type):

        if not self.config.compressor_enabled:
            return html

        compression_type = compression_type.lower()
        html_hash = self.make_hash(html)

        if not os.path.exists(u(self.config.compressor_output_dir)):
            os.makedirs(u(self.config.compressor_output_dir))

        cached_file = os.path.join(
            u(self.config.compressor_output_dir),
            u('{hash}.{extension}').format(
                hash=html_hash,
                extension=compression_type,
            ),
        )

        if os.path.exists(cached_file):
            filename = os.path.join(
                u(self.config.compressor_static_prefix),
                os.path.basename(cached_file),
            )
            return self.render_element(filename, compression_type)

        assets = OrderedDict()
        soup = BeautifulSoup(html)
        for count, c in enumerate(self.find_compilable_tags(soup)):

            url = c.get('src') or c.get('href')
            if url:
                filename = os.path.basename(u(url)).split('.', 1)[0]
                uri_cwd = os.path.join(u(self.config.compressor_static_prefix),
                                       os.path.dirname(u(url)))
                text = open(self.find_file(u(url)), 'r', encoding='utf-8')
                cwd = os.path.dirname(text.name)
            else:
                filename = u('inline{0}').format(count)
                uri_cwd = None
                text = c.string
                cwd = None

            mimetype = c['type'].lower()
            try:
                compressor = self.config.compressor_classes[mimetype]
            except KeyError:
                msg = u('Unsupported type of compression {0}').format(mimetype)
                raise RuntimeError(msg)

            text = self.get_contents(text)
            compressed = compressor.compile(text,
                                            mimetype=mimetype,
                                            cwd=cwd,
                                            uri_cwd=uri_cwd,
                                            debug=self.config.compressor_debug)

            if not self.config.compressor_debug:
                outfile = cached_file
            else:
                outfile = os.path.join(
                    u(self.config.compressor_output_dir),
                    u('{hash}-{filename}.{extension}').format(
                        hash=html_hash,
                        filename=filename,
                        extension=compression_type,
                    ),
                )

            if assets.get(outfile) is None:
                assets[outfile] = u('')
            assets[outfile] += u("\n") + compressed

        blocks = u('')
        for outfile, asset in assets.items():
            with open(outfile, 'w', encoding='utf-8') as fh:
                fh.write(asset)
            filename = os.path.join(
                u(self.config.compressor_static_prefix),
                os.path.basename(outfile),
            )
            blocks += self.render_element(filename, compression_type)

        return blocks