1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

122

123

124

"""Page CMS functions related to the ``request`` object.""" 

from django.core.handlers.base import BaseHandler 

from django.core.handlers.wsgi import WSGIRequest 

from django.http import HttpResponse 

from django.shortcuts import render_to_response 

from django.template import RequestContext 

from django.core.urlresolvers import reverse 

from pages import settings 

 

def get_request_mock(): 

    """Build a ``request`` mock up that can be used for testing.""" 

    basehandler = BaseHandler() 

    basehandler.load_middleware() 

    request = WSGIRequest({ 

        'REQUEST_METHOD': 'GET', 

        'SERVER_NAME': 'test', 

        'SERVER_PORT': '8000', 

        'HTTP_HOST': 'testhost', 

    }) 

    # Apply request middleware 

    for middleware_method in basehandler._request_middleware: 

        # LocaleMiddleware should never be applied a second time because 

        # it would broke the current real request language 

        if 'LocaleMiddleware' not in str(middleware_method.im_class): 

            response = middleware_method(request) 

    return request 

 

class AutoRenderHttpError(Exception): 

    """Cannot return context dictionary because a view returned an 

    ``HttpResponse`` when a (template_name, context) tuple was expected.""" 

    pass 

 

def auto_render(func): 

    """ 

    This view decorator automatically calls the ``render_to_response`` 

    shortcut. A view that use this decorator should return a tuple of this 

    form : (template name, context) instead of a ``HttpRequest`` object. 

    """ 

    def auto_render_decorator(request, *args, **kwargs): 

        template_override = kwargs.pop('template_name', None) 

        only_context = kwargs.pop('only_context', False) 

        only_response = kwargs.pop('only_response', False) 

        if only_context or only_response: 

            # return only context dictionary or response 

            response = func(request, *args, **kwargs) 

            if only_response: 

                return response 

            if isinstance(response, HttpResponse): 

                raise AutoRenderHttpError 

            (template_name, context) = response 

            return context 

        response = func(request, *args, **kwargs) 

        if isinstance(response, HttpResponse): 

            return response 

        (template_name, context) = response 

        template_name = context['template_name'] = template_override or template_name 

        return render_to_response(template_name, context, 

                            context_instance=RequestContext(request)) 

    return auto_render_decorator 

 

def pages_view(view): 

    """ 

    Provide the essential pages variables to the decorated view 

    by using the default pages.views.details view. 

    """ 

    def pages_view_decorator(request, *args, **kwargs): 

        path = kwargs.pop('path', None) 

        lang = kwargs.pop('lang', None) 

        if path or lang: 

            from pages.views import details 

            response = details(request, path=path, lang=lang, 

                only_context=True, delegation=False) 

            context = response 

            kwargs.update(context) 

        return view(request, *args, **kwargs) 

    return pages_view_decorator 

 

 

def get_slug_and_relative_path(path, lang=None): 

    """ 

    Return the page's slug, relative path and language. 

     

        >>> get_slug_and_relative_path('/test/function/') 

        ('function', 'test/function', None) 

    """ 

    root = reverse('pages-root') 

    if path.startswith(root): 

        path = path[len(root):] 

    if len(path) and path[-1] == '/': 

        path = path[:-1] 

    slug = path.split("/")[-1] 

    if settings.PAGE_USE_LANGUAGE_PREFIX: 

        lang = path.split("/")[0] 

        path = path[(len(lang) + 1):] 

    return slug, path, lang 

 

def get_template_from_request(request, page=None): 

    """ 

    Gets a valid template from different sources or falls back to the 

    default template. 

    """ 

    page_templates = settings.get_page_templates() 

    if len(page_templates) == 0: 

        return settings.PAGE_DEFAULT_TEMPLATE 

    template = request.REQUEST.get('template', None) 

    if template is not None and \ 

            (template in dict(page_templates).keys() or 

            template == settings.PAGE_DEFAULT_TEMPLATE): 

        return template 

    if page is not None: 

        return page.get_template() 

    return settings.PAGE_DEFAULT_TEMPLATE 

 

def get_language_from_request(request): 

    """Return the most obvious language according the request.""" 

    language = request.GET.get('language', None) 

    if language: 

        return language 

 

    if hasattr(request, 'LANGUAGE_CODE'): 

        return settings.PAGE_LANGUAGE_MAPPING(str(request.LANGUAGE_CODE)) 

    else: 

        return settings.PAGE_DEFAULT_LANGUAGE