Example #1
0
 def put_resource(self, bundle_name, name, cache_seconds, content):
     """Puts a Resource in the datastore for testing, and tracks it to
     be cleaned up in test teardown."""
     bundle = ResourceBundle(key_name=bundle_name)
     key = Resource(parent=bundle, key_name=name, content=content,
                    cache_seconds=float(cache_seconds)).put()
     self.temp_entity_keys.append(key)
    def test_resource_override(self):
        """Verifies that Resources in the datastore override files on disk."""
        # Should render normally.
        doc = self.go('/haiti/create')
        assert 'xyz' not in doc.content

        # This Resource should override the create.html.template file.
        bundle = ResourceBundle(key_name='1')
        key1 = Resource(parent=bundle,
                        key_name='create.html.template',
                        content='xyz{{env.repo}}xyz').put()
        doc = self.go('/haiti/create')
        assert 'xyzhaitixyz' not in doc.content  # old template is still cached

        # The new template should take effect after 1 second.
        self.advance_utcnow(seconds=1.1)
        doc = self.go('/haiti/create')
        assert 'xyzhaitixyz' in doc.content

        # A plain .html Resource should override the .html.template Resource.
        key2 = Resource(parent=bundle,
                        key_name='create.html',
                        content='xyzxyzxyz').put()
        self.advance_utcnow(seconds=1.1)
        doc = self.go('/haiti/create')
        assert 'xyzxyzxyz' in doc.content

        # After removing both Resources, should fall back to the original file.
        db.delete([key1, key2])
        self.advance_utcnow(seconds=1.1)
        doc = self.go('/haiti/create')
        assert 'xyz' not in doc.content
def put_bundle(new_bundle_name, original_bundle_name=None):
    """Puts a new ResourceBundle, optionally copying from another bundle."""
    new_bundle = ResourceBundle(key_name=new_bundle_name)
    entities = [new_bundle]
    if original_bundle_name:
        original_bundle = ResourceBundle.get_by_key_name(original_bundle_name)
        original_resources = Resource.all().ancestor(original_bundle)
        entities += [Resource(parent=new_bundle,
                              key_name=resource.key().name(),
                              cache_seconds=resource.cache_seconds,
                              content=resource.content)
                     for resource in original_resources]
    db.put(entities)
    def test_resource_caching(self):
        """Verifies that Resources are cached properly."""
        # There's no file here.
        self.go('/global/foo.txt')
        assert self.s.status == 404
        self.go('/global/foo.txt?lang=fr')
        assert self.s.status == 404

        # Add a Resource to be served as the static file.
        bundle = ResourceBundle(key_name='1')
        Resource(parent=bundle, key_name='static/foo.txt',
                 content='hello').put()
        doc = self.go('/global/foo.txt?lang=fr')
        assert doc.content_bytes == 'hello'

        # Add a localized Resource.
        fr_key = Resource(parent=bundle,
                          key_name='static/foo.txt:fr',
                          content='bonjour').put()
        doc = self.go('/global/foo.txt?lang=fr')
        assert doc.content_bytes == 'hello'  # original Resource remains cached

        # The cached version should expire after 1 second.
        self.advance_utcnow(seconds=1.1)
        doc = self.go('/global/foo.txt?lang=fr')
        assert doc.content_bytes == 'bonjour'

        # Change the non-localized Resource.
        Resource(parent=bundle, key_name='static/foo.txt',
                 content='goodbye').put()
        doc = self.go('/global/foo.txt?lang=fr')
        assert doc.content_bytes == 'bonjour'
        # no effect on the localized Resource

        # Remove the localized Resource.
        db.delete(fr_key)
        doc = self.go('/global/foo.txt?lang=fr')
        assert doc.content_bytes == 'bonjour'
        # localized Resource remains cached

        # The cached version should expire after 1 second.
        self.advance_utcnow(seconds=1.1)
        doc = self.go('/global/foo.txt?lang=fr')
        assert doc.content_bytes == 'goodbye'
Example #5
0
    def handle(self, operation):
        """Handles both GET and POST requests.  POST requests include an
        'operation' param describing what the user is trying to change."""
        bundle_name = self.params.resource_bundle or ''
        name = self.params.resource_name or ''
        lang = self.params.resource_lang or ''
        key_name = name + (lang and ':' + lang)
        editable = (bundle_name != self.env.default_resource_bundle)
        if not ResourceBundle.get_by_key_name(
                self.env.default_resource_bundle):
            ResourceBundle(key_name=self.env.default_resource_bundle).put()

        if operation == 'set_preview':
            # Set the resource_bundle cookie.  This causes all pages to render
            # using the selected bundle (see main.py).  We use a cookie so that
            # it's possible to preview PF as embedded on external sites.
            self.response.headers['Set-Cookie'] = \
                'resource_bundle=%s; path=/' % bundle_name
            return self.redirect(self.get_admin_url())

        if operation == 'set_default':
            # Set the default resource bundle.
            config.set(
                default_resource_bundle=self.params.resource_bundle_default)
            return self.redirect(self.get_admin_url())

        if operation == 'add_bundle' and editable:
            # Add a new bundle, optionally copying from an existing bundle.
            put_bundle(bundle_name, self.params.resource_bundle_original)
            return self.redirect(self.get_admin_url(bundle_name))

        if operation == 'add_resource' and editable:
            # Go to the edit page for a new resource (don't create until save).
            return self.redirect(self.get_admin_url(bundle_name, name, lang))

        if operation == 'delete_resource' and editable:
            # Delete a resource.
            resource = Resource.get(key_name, bundle_name)
            if resource:
                resource.delete()
            return self.redirect(self.get_admin_url(bundle_name))

        if operation == 'put_resource' and editable:
            # Store the content of a resource.
            if isinstance(self.request.POST.get('file'), cgi.FieldStorage):
                content = self.request.get('file')  # uploaded file content
            elif 'content' in self.request.POST:  # edited text
                content = self.request.get('content').encode('utf-8')
            else:  # modify cache_seconds but leave content unchanged
                resource = Resource.get(key_name, bundle_name)
                content = resource and resource.content or ''
            put_resource(bundle_name,
                         key_name,
                         content=content,
                         cache_seconds=self.params.cache_seconds)
            return self.redirect(self.get_admin_url(bundle_name))

        if not operation:
            self.write(PREFACE + self.format_nav_html(bundle_name, name, lang))
            if bundle_name and name:
                self.show_resource(bundle_name, key_name, name, lang, editable)
            elif bundle_name:
                self.list_resources(bundle_name, editable)
            else:
                self.list_bundles()
Example #6
0
def put_resource(bundle_name, key_name, **kwargs):
    """Puts a Resource in the datastore under the specified ResourceBundle."""
    bundle = ResourceBundle(key_name=bundle_name)
    Resource(parent=bundle, key_name=key_name, **kwargs).put()