🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Thread View: pl.comp.lang.python
4 messages
4 total messages Started by news Thu, 23 Jul 2009 21:54
django, wiele języków i wiele domen
#26429
Author: news
Date: Thu, 23 Jul 2009 21:54
89 lines
3681 bytes
Witam,

Mam problem z Django - próbuję zrobić serwis który będzie działał na kilku
domenach i dla każdej domeny będzie inny język.

Czyli np.
domena.com -> język ang.
innadomena.pl -> język polski

Przy okazji jak wchodzimy na różne domeny, to odpowiednio zmienia się
SITE_ID.

Do dynamicznej zmiany Site użyłem czegoś na wzór tego snippeta:
# http://www.djangosnippets.org/snippets/1099/

Czyli w settings.py jest:
from threading import local
SITE_THREAD_INFO = local()
SITE_THREAD_INFO.SITE_ID = 1
class SiteIDHook(object):
    def __int__(self):
        return SITE_THREAD_INFO.SITE_ID
    def __hash__(self):
        return SITE_THREAD_INFO.SITE_ID
SITE_ID = SiteIDHook()


Dodaje middleware który to obsługuje, i przy okazji dołączam w nim coś na
wzór LocaleMiddleware - ma dynamicznie zmieniać LANGUAGE_CODE...:

middleware.py:
from django.conf import settings
from django.contrib.sites.models import Site
from django.http import HttpResponseRedirect

from django.utils.cache import patch_vary_headers
from django.utils import translation


import logging
log = logging.getLogger('multisite')


class MultiSiteMiddleware(object):
    def process_request(self, request):
        settings.SITE_THREAD_INFO.SITE_ID = 1

        host = request.META.get('HTTP_HOST').split(':')[0]
        if host.startswith('www.'): host = host[4:]

        log.debug('host=' + host)

        if host:
            try:
                site = Site.objects.get(domain=host)
                settings.SITE_THREAD_INFO.SITE_ID = site.id
                if '.pl' in host:
                    translation.activate('pl-pl')
                    request.LANGUAGE_CODE = translation.get_language()
                    log.debug('wersja PL')
                else:
                    translation.activate(settings.LANGUAGE_CODE)
                    request.LANGUAGE_CODE = translation.get_language()
                    log.debug('wersja EN ' + settings.LANGUAGE_CODE)

            except Site.DoesNotExist:
                settings.SITE_THREAD_INFO.SITE_ID = 1

    def process_response(self, request, response):
        patch_vary_headers(response, ('Accept-Language',))
        if 'Content-Language' not in response:
            response['Content-Language'] = translation.get_language()
        translation.deactivate()
        return response


middleware.py jest załączony zaraz za SessionMiddleware - tak jak sugerują
w docach.

A teraz problem: otóz Django 'wariuje' - potrafi na jednej stronie pokazać
niektóre teksty przetłumaczone, a inne nie. Wystarczy że w przeglądarce
otworze domena.com (i troche pochodze) a w drugiej zakładce innadomena.pl i
też trochę poklikam.

Może ktoś poradzić co tu może być nie tak? Coś z wątkami w Django?


Pozdr
MS
Re: django, wiele języków i wiele domen
#26430
Author: Darek
Date: Fri, 24 Jul 2009 10:01
105 lines
4864 bytes
On Jul 23, 11:54 pm, news <exam...@example.com> wrote:
> Witam,
>
> Mam problem z Django - próbuję zrobić serwis który będzie działał na kilku
> domenach i dla każdej domeny będzie inny język.
>
> Czyli np.
> domena.com -> język ang.
> innadomena.pl -> język polski
>
> Przy okazji jak wchodzimy na różne domeny, to odpowiednio zmienia się
> SITE_ID.
>
> Do dynamicznej zmiany Site użyłem czegoś na wzór tego snippeta:
> #http://www.djangosnippets.org/snippets/1099/
>
> Czyli w settings.py jest:
> from threading import local
> SITE_THREAD_INFO = local()
> SITE_THREAD_INFO.SITE_ID = 1
> class SiteIDHook(object):
>     def __int__(self):
>         return SITE_THREAD_INFO.SITE_ID
>     def __hash__(self):
>         return SITE_THREAD_INFO.SITE_ID
> SITE_ID = SiteIDHook()
>
> Dodaje middleware który to obsługuje, i przy okazji dołączam w nim coś na
> wzór LocaleMiddleware - ma dynamicznie zmieniać LANGUAGE_CODE...:
>
> middleware.py:
> from django.conf import settings
> from django.contrib.sites.models import Site
> from django.http import HttpResponseRedirect
>
> from django.utils.cache import patch_vary_headers
> from django.utils import translation
>
> import logging
> log = logging.getLogger('multisite')
>
> class MultiSiteMiddleware(object):
>     def process_request(self, request):
>         settings.SITE_THREAD_INFO.SITE_ID = 1
>
>         host = request.META.get('HTTP_HOST').split(':')[0]
>         if host.startswith('www.'): host = host[4:]
>
>         log.debug('host=' + host)
>
>         if host:
>             try:
>                 site = Site.objects.get(domain=host)
>                 settings.SITE_THREAD_INFO.SITE_ID = site.id
>                 if '.pl' in host:
>                     translation.activate('pl-pl')
>                     request.LANGUAGE_CODE = translation.get_language()
>                     log.debug('wersja PL')
>                 else:
>                     translation.activate(settings.LANGUAGE_CODE)
>                     request.LANGUAGE_CODE = translation.get_language()
>                     log.debug('wersja EN ' + settings.LANGUAGE_CODE)
>
>             except Site.DoesNotExist:
>                 settings.SITE_THREAD_INFO.SITE_ID = 1
>
>     def process_response(self, request, response):
>         patch_vary_headers(response, ('Accept-Language',))
>         if 'Content-Language' not in response:
>             response['Content-Language'] = translation.get_language()
>         translation.deactivate()
>         return response
>
> middleware.py jest załączony zaraz za SessionMiddleware - tak jak sugerują
> w docach.
>
> A teraz problem: otóz Django 'wariuje' - potrafi na jednej stronie pokazać
> niektóre teksty przetłumaczone, a inne nie. Wystarczy że w przeglądarce
> otworze domena.com (i troche pochodze) a w drugiej zakładce innadomena.pl i
> też trochę poklikam.
>
> Może ktoś poradzić co tu może być nie tak? Coś z wątkami w Django?
>
> Pozdr
> MS

Bradzo "głupie" rozwiązanie i nie polecam jego stosowania. Takie
rzeczy najlepiej robić użuwając konfiguracji serwera. Przykład Apache:

<VirtualHost mysite.pl:80>
...
SetEnv DJANGO_SETTINGS_MODULE mysite.settings_pl
...
</VirtualHost>

<VirtualHost mysite.com:80>
...
SetEnv DJANGO_SETTINGS_MODULE mysite.settings_com
...
</VirtualHost>

--settings_com.py--
from mysite.settings import *
# nadpisujesz co chcesz...
SITE_ID = 2
Re: django, wiele języków i wiele domen
#26431
Author: news
Date: Fri, 24 Jul 2009 11:25
27 lines
1794 bytes
> Bradzo "głupie" rozwiązanie i nie polecam jego stosowania. Takie
> rzeczy najlepiej robić użuwając konfiguracji serwera. Przykład Apache:
> 
> <VirtualHost mysite.pl:80>
> ...
> SetEnv DJANGO_SETTINGS_MODULE mysite.settings_pl
> ...
> </VirtualHost>
> 
> <VirtualHost mysite.com:80>
> ...
> SetEnv DJANGO_SETTINGS_MODULE mysite.settings_com
> ...
> </VirtualHost>
> 
> --settings_com.py--
> from mysite.settings import *
> # nadpisujesz co chcesz...
> SITE_ID = 2


OK, problem chyba rozwiązany  - chodziło o użycie ugettext zamiast
ugettext_lazy... 

Przy okazji - można wiedzieć czemu "bradzo głupie"? Podmiana SITE_ID działa
zupełnie dobrze, zaś podmiana LANGUAGE_CODE jest w zasadzie przepisana ze
źródeł Django (middleware/locale.py). Więc nie wiem o co ci chodzi.
Re: django, wiele języków i wiele domen
#26432
Author: Darek
Date: Fri, 24 Jul 2009 17:14
46 lines
3418 bytes
On Jul 24, 1:25 pm, news <exam...@example.com> wrote:
> > Bradzo "głupie" rozwiązanie i nie polecam jego stosowania. Takie
> > rzeczy najlepiej robić użuwając konfiguracji serwera. Przykład Apache:
>
> > <VirtualHost mysite.pl:80>
> > ...
> > SetEnv DJANGO_SETTINGS_MODULE mysite.settings_pl
> > ...
> > </VirtualHost>
>
> > <VirtualHost mysite.com:80>
> > ...
> > SetEnv DJANGO_SETTINGS_MODULE mysite.settings_com
> > ...
> > </VirtualHost>
>
> > --settings_com.py--
> > from mysite.settings import *
> > # nadpisujesz co chcesz...
> > SITE_ID = 2
>
> OK, problem chyba rozwiązany  - chodziło o użycie ugettext zamiast
> ugettext_lazy...
>
> Przy okazji - można wiedzieć czemu "bradzo głupie"? Podmiana SITE_ID działa
> zupełnie dobrze, zaś podmiana LANGUAGE_CODE jest w zasadzie przepisana ze
> źródeł Django (middleware/locale.py). Więc nie wiem o co ci chodzi.

Widze, że bardziej skopiowałeś kod z jakiś snippetów niż się nad nim
zastanowiłeś. To nawet nie do końca jest monkey-patching, ingerujesz w
ustawienia w trakcie wykonywania, w które nie powinieneś. Ustawienia
SITE nieprzypadkowo znalazły się w settings.py. Poza tym sama idea
obsługi tego przez wątki, kiedy są inne wyjścia (np. to o którym
wspomniałem wyżej) jest w tym miejscu niewłaściwa. Była kiedyś
dyskusja na django-developers a propos używania takiego podejścia do
przechowywania np. obiektu request, dzieki czemu można było mieć
dostęp do niego z każdego miejsca, choć to troche problem innej
kategorii bo nie wszedzie można przekazać request jako parametr, to
jednak sprawa ta niezostała ani jednoznacznie poparta, czy też
kategorycznie odrzucona, z tego co wiem to mają się z tym problemem
zmierzyć developerzy w którejś wersji farmeworka.

Co do zmiany języka, zauważ, że nie robisz zmian na ustawieniach, ale
na obiekcie request w middleware co jest poprawne (poza tym Django
dostarcza metod do zmiany języka, wystarczy tylko zmapować sobie je na
własne URLe)
Thread Navigation

This is a paginated view of messages in the thread with full content displayed inline.

Messages are displayed in chronological order, with the original post highlighted in green.

Use pagination controls to navigate through all messages in large threads.

Back to All Threads