Django Subdomain - python

I'm trying to make a basic store app. I've set up a database so that every product is tied to a particular store: let's call the stores Shoes, Toys, and Books.. I need to set up subdomains for the app (it's in the assignment specs, no choice there) so that I can map to shoes.myapp.com, toys.myapp.com and books.myapp.com. What I think I need to do is somehow set up the subdomain (which I've googled but am confused about: is this the way to go?) and then, I guess, filter my databases from the info in the subdomain so that only products that have the store name "Shoes" for example appear on the page. Am I anywhere approaching the right track or is there a much better way to structure this?

I suggest you to use this application: django-subdomains. http://django-subdomains.readthedocs.org/en/latest/index.html
And then, in your settings.py, you should use:
SUBDOMAIN_URLCONF = {
'toys': 'yourproject.urls.toys',
'shoes': 'yourproject.urls.shoes'
(...)
}
If you need to use the name of the subdomain in a view, it will be attached to the request object:
def your_view(request):
subdomain = request.subdomain
products = Products.objects.filter(store=subdomain) #an example how to use it to specif database queries. I dont know how your models are

Related

Dynamic database selection based on URL in Django

Let's say the first page of the app has two links. Is it possible to pick the database depending on which link is clicked? The databases both have the same models, but different data. For example, let's say the application contains students for different colleges A and B. If link for A is clicked, then database for A is used which contains the students for college A. The entire application after this point should use database for college A.
I understand there are ways to work around this problem by just designing the databases differently, i.e. having a college field, and just filtering out students with the particular college affiliation. But I am hoping to find a solution using Django to just use two different databases.
So you need to store the chosen database in session or smth and you can easily pick the database. From the docs
>>> # This will run on the 'default' database.
>>> Author.objects.all()
>>> # So will this.
>>> Author.objects.using('default').all()
>>> # This will run on the 'other' database.
>>> Author.objects.using('other').all()
You could mix together Database Routers with this GlobalRequestMiddleware solution to create a database router which inspects the request to figure out which database to use.
class RequestDatabaseRouter(object):
def db_for_read(self, model, **hints):
request = GlobalRequestMiddleware.get_current_request()
key = self.get_database_key(request) # Implement get_database_key
return key
There may be some way to inject the request into **hints, which I think would be preferable over the Middleware solution, however, I'm unaware how to at the moment. You may need to make sure the GlobalRequestMiddleware is called after the AuthenticationMiddleware otherwise you may not have the user on the request to inspect.

Global Variables in Django Admin Site

This was my original question, but it was not answered and so I thought Id post again with some of the strategies that I have tried, and be a little more specific.
I want to create a dynamic admin site, that based on if the field is blank or not will show that field. So I have a model that has a set number of fields, but for each individual entry will not contain all of the fields in my model and I want to exclude based on if that field is blank. My project is about bridges, and so to put it in practical terms I have a model that has every bridge part in it (this roughly is equivalent to 100), but each individual bridge (mapped to each unique brkey) will not have all 100 bridge parts. And so, I can prepopulate all of the fields it does have, but then the admin site has 100 other fields, and I would like to not display those fields that were not used on my admin site for that specific bridge, but those fields will differ with pretty much every bridge.
Like I said before, I have a unique bridge identifier(a unique 15 digit string), that correlates to each bridge, and then all of the various different variables that describe the bridge.
I have it set up now that the user will go to a url with the unique bridgekey and then this will create an entry of that bridge. So (as i am testing on my local machine) it would be like localhost/home/brkey and that code in my views.py that corresponds to that url is
Is this a final route that I have to take? I am very new to JavaScript and so I do not want to take this route but I will if I have to. Also does Django use Javascript in anyway that is syntactically different? If so I cannot find any Django documentation on incorporating Javascript into my admin site.
A final option that I have exhausted is to use global variables. Instead of having the url that creates the entry in my Views.py, I placed it in my admins.py, and had my modelAdmin class in there as well, so like this.
admins.py
-set up global variable
bridgekey_unique = " "
If I can find a way to either pass that unique bridge key to my modelAdmin class, or figure out if that said field is blank because the bridge doesnt have that part, I will be able to achieve what I want without using Javascript. I have tried a lot of variations of all two of theses strategies to no avail, but have not tried the JavaScript idea as I dont really know any javascript at all.
Sorry for the lengthy post, but people said I wasnt specific enough. Any help would be greatly appreciated.
I didn't read all of that - sorry, there's too much. But I did notice your comment that you expect to access in your modeladmin definition a variable that you set in your view. That can't possibly work.
Anything at class level is always executed when the module containing the class is first imported. That is when the server process starts up, so there is no possible way anything done in the view can have happened yet.
You almost never want to have any logic at class level. You need to put it in methods, which are called at the relevant time. In this case, you probably need to use the get_fields method.
Edit
Looking further up at your attempt at a get_fields method, I can't see at all what you are trying to do here. 'prestressed_concrete_deck' is a literal string, and could never be None, so neither of your conditions can ever be true. And as to your question about what the parameters are, the documentation for that method explains clearly that obj is the object being edited.

How can I share a selected amount of data with all my templates in pyramid?

I read the cookbook article on making user objects avail to all requests but I may not understand it fully because I can't see if it is related to my problem.
I render quite a few templates on a site I'm working on and there's different user info each templates needs. For example, like this page on SO my every page needs to display my username, points, number of notifications, number of badges, etc. I have all this information but I find myself having to add it to each request dictionary I send to the template like so:
return dict(page=page, name=name, save_url=save_url,
logged_in=authenticated_userid(request), title='add new', url='/new', points=points, num_badges=badges)
Is there a way to combine all this once so I can just send one entry to each view? I'm sure its not good to run the same query every time but its also annoying to have to type it for every view. Any suggestions?
The simplest method would be to generate your 'common' information in one method, returning a dict, then updating your local view dict with that information
local = dict(page=page, name=name, save_url=save_url, title='add new',
url='/new', points=points, num_badges=badges)
local.update(retrieve_common_information(request))
return local
Another method is to use something like the pyramid_viewgroup (documentation now located at a new location), where you delegate the rendering of common 'snippets' of your pages to separate views.
One such view could take care of the common user information you want to render, and be reused everywhere.

Can namespaces enable multiple domains?

My gae app serves multiple domains by if..else.. conditions rather than namespaces.
I see someone else solved it with namespaces
"I have a single app with multiple namespaces defined.
I'd like to set up multiple domains
a.com b.com c.com
and have the app detect the domain and write the domain's data into
its respective namespace."
I don't know how to do it with namespaces and I want a better way to add a domain to the app for settings like content and languages. For example sending an email via a form then I use just a condition instead of namespace.
class FileUploadHandler(blobstore_handlers.BlobstoreUploadHandler):
def post(self):
adminemail = 'admin#domain1.com' if gethost() is 'domain1' else 'admin#domain2.com'
message = mail.EmailMessage(sender=admin_email, subject=self.request.POST.get('subject'))
message.body = ...
message.to='info#domain...
message.send()
self.redirect('/customer_service.htm')
I use same workaround for queries, localization and in some cases even which template to render to while I should be able to make all domains able to be based on same templates and differ only by content so that my app doesn't hard-code the domains and other settings that should be easy to add and change.
Are namespaces a great idea in this case? The way a managed the problem with different domains so far is a variable for the entity which domains it came from
if util.get_host().find('my-dot-com') > 0:
url = 'www.my-dot-com.com'
I have a function that defines what I mean but it may confuse www.domain.com with domain.com or have problems with subdomains
def get_host():
return os.environ.get("HTTP_HOST", os.environ["SERVER_NAME"])
I'd be glad to know any idea if you have, or if I'm mistaken and shouldn't use namespaces in this case.
Thanks
Yes, namespaces are ideally suited to what you're doing. Simply store configuration data like admin emails in a per-domain configuration record, and store all the records for a given domain in a namespace named after that domain.

Django admin site: how to create a single page for global settings?

I would like to create a single page in the admin site of django where I can change some global variables of the website (title of the website, items in the navigation menu, etc). At the moment I have them coded as context processors but I would like to make them editable. Something similar to what happens in WordPress.
Is this possible?
I can store the data in the databse, but can I have a link in the admin site that goes straight to the first document record and doesnt allow the creation of multiple records (they wouldnt make sense)
Instead of creating a model in the database, would it be possible to change some context_processor from the admin site (I think this would be best)
django-preferences does exactly what you are looking for. The implementation is a bit hacky (particularly the setting of __module__ on the model class to trick Django into thinking it was loaded from a different app), but it works.
This sounds like what the sites framework is intended to help with.
http://docs.djangoproject.com/en/stable/ref/contrib/sites/
"It’s a hook for associating objects and functionality to particular Web sites, and it’s a holding place for the domain names and “verbose” names of your Django-powered sites."
The docs make it sound like it's only good for multiple sites, but it's a great place to put stuff in a single-site-per-django model too.
There's an app called django-values that allows you storing of specific settings in the database.

Categories