Django FileFields not uploading (I've gone through the proper steps...) - django

I want to enable my users to upload photos. Because of local development issues (I'm on windows), I've used FileFields for the time being rather than ImageFields. On my local server, everything was working just fine. I've also uploaded images remotely in the past, so I know the drill.
For some reason, it's now failing to write the files to the specified directory. I pulled the directory as a part of my general git pull. Could that be the issue.
I've done all the following
Model:
class Post_Photo(models.Model):
post=models.ForeignKey(Post,blank=True,null=True)
photo=models.FileField(upload_to="post_photos")
Settings file:
MEDIA_ROOT = '/path..../public_html/media/' (tried with and w/o trailing slash)
I've changed both the /media and /media/post_photos permissions so that they are writable by apache (www-data).
chgrp www-data post_photos
chmod g+w post_photos
I guess I can try to make it permissions 777. Has anybody run into this problem?

Apparently your MEDIA_URLpoints to example.com. Change it to the address of your site.
file settings.py, look for:
# URL that handles the media served from MEDIA_ROOT. Make sure to use a
# trailing slash if there is a path component (optional in other cases).
# Examples: "http://media.lawrence.com", "http://example.com/media/"
MEDIA_URL = ''

Related

Nginx permissions

I deployed the server with Ubuntu 18, Django, Gunicorn, Nginx
And I ran into this problem:
everything works great but,
When I upload large pictures files in Django, Nginx gives 403 Error Forbidden.
I updated the permissions to the folder with static files on 755. It works!
But when I upload other files, the rights do not work.
I added the user root and user www-data to the folder owner’s group, but nothing has changed.
I understand that Nginx has no permissions, but how can I implement the inheritance permissions of new files from the parent folder
or will you suggest another solution?
You need to add FILE_UPLOAD_PERMISSIONS=0o644 variable to you settings.py file.
This is the numeric mode (i.e. 0o644) to newly uploaded files to.
For more information, please read this doc.
Try use this
chown -R www-data:www-data 'your project folder'

django-compressor not setting absolute CSS image paths on Heroku

I'm using django-compressor to concatenate and compress my CSS and JS files on this site. I'm serving static files from an S3 bucket.
On my local copy of the site, using a different S3 bucket, this all works perfectly. But on the live site, hosted on Heroku, it all works except the relative URLs for images in the CSS files do not get re-written.
eg, this line in the CSS file:
background-image: url("../img/glyphicons-halflings-grey.png");
gets rewritten to:
background-image:url('https://my-dev-bucket-name.s3.amazonaws.com/static/img/glyphicons-halflings-grey.png')
on my development site, but isn't touched on the live site. So the live site ends up looking in pepysdiary.s3.amazonaws.com/static/CACHE/img/ for the images (as it's relative to the new, compressed CSS file).
For now, I've put a directory at that location containing the images, but I can't work out why there's this difference. Both sites have this in their settings:
COMPRESS_CSS_FILTERS = [
# Creates absolute urls from relative ones.
'compressor.filters.css_default.CssAbsoluteFilter',
# CSS minimizer.
'compressor.filters.cssmin.CSSMinFilter'
]
And the CSS files are being minimised just fine... but it's like the other filter isn't being applied on the live site.
I recently ran into this issue on heroku, and running the latest version of django-compressor (1.3) does not solve the problem. I will provide the solution that I am using, as well as an explanation of the problems I ran into along the way.
The solution
I created my own 'CssAbsoluteFilter' that removes the settings.DEBUG check from the 'find' method like this:
# compress_filters.py
from compressor.filters.css_default import CssAbsoluteFilter
from compressor.utils import staticfiles
class CustomCssAbsoluteFilter(CssAbsoluteFilter):
def find(self, basename):
# The line below is the original line. I removed settings.DEBUG.
# if settings.DEBUG and basename and staticfiles.finders:
if basename and staticfiles.finders:
return staticfiles.finders.find(basename)
# settings.py
COMPRESS_CSS_FILTERS = [
# 'compressor.filters.css_default.CssAbsoluteFilter',
'app.compress_filters.CustomCssAbsoluteFilter',
'compressor.filters.cssmin.CSSMinFilter',
]
The absolute urls now always work for me whether DEBUG = True or False.
The Problem
The issue is connected to 'compressor.filters.css_default.CssAbsoluteFilter', your DEBUG setting, and the fact that heroku has a read-only file system and overwrites your app files every time you deploy.
The reason compress works correctly on your development server is because CssAbsoluteFilter will always find your static files when DEBUG = True, even if you never run 'collectstatic'. It looks for them in STATICFILES_DIRS.
When DEBUG = False on your production server, CssAbsoluteFilter assumes that static files have already been collected into your COMPRESS_ROOT and won't apply the absolute filter if it can't find the files.
Jerdez, django-compressor's author, explains it like this:
the CssAbsoluteFilter works with DEBUG = False if you've successfully provided the files to work with. During development compressors uses the staticfiles finder as a convenience so you don't have to run collectstatic all the time.
Now for heroku. Even though you are storing your static files on S3, you need to also store them on heroku (using CachedS3BotoStorage). Since heroku is a read-only file system, the only way to do this is to let heroku collect your static files automatically during deployment (see https://devcenter.heroku.com/articles/django-assets).
In my experience, running 'heroku run python manage.py collectstatic --noinput' manually or even in your Procfile will upload the files to S3, but it will NOT save the files to your STATIC_ROOT directory (which compressor uses by default as the COMPRESS_ROOT). You can confirm that your static files have been collected on heroku using 'heroku run ls path/to/collected'.
If your files have been collected on heroku successfully, you should be able to compress your files successfully as well, without the solution I provided above.
However, it seems heroku will only collect static files if you have made changes to your static files since your last deploy. If no changes have been made to your static files, you will see something like "0 of 250 static files copied". This is a problem because heroku completely replaces your app contents when you deploy, so you lose whatever static files were previously collected in COMPRESS_ROOT/STATIC_ROOT. If you try to compress your files after the collected files no longer exist on heroku and DEBUG = False, the CssAbsoluteFilter will not replace the relative urls with absolute urls.
My solution above avoids the heroku problem altogether, and replaces relative css urls with absolute urls even when DEBUG = False.
Hopefully other people will find this information helpful as well.
I've had this exact same problem for a month now, but this is fixed in the 1.3 release (3/18/13, so you were probably on 1.2), so just upgrade:
pip install -U django-compressor
The exact problem I gave up on working out, but it's related to Heroku and CssAbsoluteFilter being called but failing at _converter method. Looking at the 1.3 changelog, the only related commit is this: https://github.com/jezdez/django_compressor/commit/8254f8d707f517ab154ad0d6d77dfc1ac292bf41
I gave up there, life's too short.
Meanwhile this has been fixed in django-compressor 1.6. From the changelog:
Apply CssAbsoluteFilter to precompiled css even when compression is disabled
i.e. the absolute filter is run even with DEBUG = True.

Serving static admin files for Django 1.5 in a shared hosting environment

I'm trying to get a fresh installation of Django 1.5 running on an Apache-Server. The WebServer is situated on a shared hosting platform called uberspace.de
which means I have no access to the Apache configuration itself I can however write .htaccess files if that's any help at all. Django is deployed via fast-cgi which is working as expected.
Whats not working however is the access to static files on the server like the .css files and graphics for the Django administration interface.
As mentioned in the official docs I used the following command to copy the static Files into my ~/html/static directory.
manage.py collectstatic
And these are the values from my settings.py:
STATIC_ROOT = '/home/bier/html/static/'
STATIC_URL = '/static/'
All I get is the infamous django 404 page when I try to access any of these Files.
I also followed the 'How to install and deploy Django' guide on my Webhosters Website to the letter. (sorry its only available in german I believe)
I already contacted the webhosters support but they don't know whats wrong.
All the solutions I've come up with so far suggest setting some sort of Alias in the Apache configuration. Which I can not do.
I'm thankful for any ideas you might have.
Try using a full address instead.
STATIC_ROOT = '/home/bier/html/static/'
STATIC_URL = 'http://www.mysite.com/static/'
Edit: Perhaps you could ask your host to setup /static/ in your Apache config:
sudo nano /etc/apache2/sites-enabled/mysite.com and add:
Alias /static/ /home/bier/html/static/
I've had a situation before where I've had to upload /static/ files manually because of a highly restrictive host (permissions). Perhaps you need to download a copy of django to your desktop and then upload the static admin file set into your /static/ directory manually?
Lastly, have you added the static files to your urls?
url(r'^static/(?P<path>.*)$','django.views.static.serve',{'document_root': '/home/bier/html/static'}),
I have more simpler solution. you need to create a directory named, let's say 'x' in "public_html" or similar location from which server serves the files by default.
Then upload all static files in directory x. (this can be done by running collectstatic locally and then upload all contents of directory STATIC_ROOT to x)
Then, change your STATIC_URL and STATIC_ROOT as follows:
STATIC_URL = '/x/'
STATIC_ROOT = os.path.join(BASE_DIR, '../public_html/x') # Path to folder

How do you configure a Django ImageField with upload_to and MEDIA_ROOT on Webfaction?

I have the following model field in a django project:
headshot = models.ImageField(upload_to='/tmp', blank=True, null=True)
settings.py
# format <project>/<app>
MEDIA_ROOT = '/home/username/webapps/django/myproject/books/media/'
I have created a directory: /home/username/webapps/django/myproject/books/media/tmp and gave it chmod 777 permissions.
I get the following error when I try to add a new image:
SuspiciousOperation at /admin/books/author/add/
Attempted access to '/tmp/Comment.png' denied.
Request Method: POST
Request URL: http://username.webfactional.com/app/admin/books/author/add/
Django Version: 1.3.1
Exception Type: SuspiciousOperation
Exception Value:
Attempted access to '/tmp/Comment.png' denied.
Exception Location: /home/username/webapps/django/lib/python2.7/django/core/files/storage.py in path, line 234
Python Executable: /usr/local/bin/python
Python Version: 2.7.1
Does anyone know what I'm doing wrong? Do I need .htaccess or some other settings to be able to write to this directory or is there something wrong with my Django config?
I would still like to know what chmod values to use and how to set MEDIA_URL. I'm thinking I might need to do something in urls.py for MEDIA_URL.
My project is set up on the webhost Webfaction if that makes a difference.
Fixed it. Seems like the answer was to use upload_to='tmp' instead of upload_to='/tmp'.
I see you've marked this as answered, but still have some questions in your answer. Here is how I have this set up, in case you are still working on it.
Set up a new app for media (via the webfaction control panel). I used the "static_only" application because it should prevent users from uploading scripts and running them. You could also use one of the "static/cgi/php". Creating a new app for this (instead of using Django and making a new view) is good practice because it will have a lower resource overheard. Django is overkill for serving static files (images, css files, javascript files, etc.).
Bind your new media (static_only, or whatever you used) app to some URL, again using the webfaction control panel. I bound mine to media..com. MEDIA_URL should be set to the URL you can access your media through, and MEDIA_ROOT should be the root directory for the media app. Thus, in my settings.py file I have:
MEDIA_ROOT = '/home/<username>/webapps/media/'
MEDIA_URL = 'http://media.<mydomain>.com/'
It's best to do the same thing for STATIC_ROOT and STATIC_URL.
As far as permissions go, the defaults should be OK - if you have troubles with that just ask.

Serving Django application from relative path

I am developing a Django application which works fine locally. In production, the application will be served from a relative path, such as www.example.com/app/.
I am using Apache with mod_wsgi, and I have configured Apache to serve the application from the relative URL:
WSGIScriptAlias /app /path/to/my/modwsgi.py
WSGIDaemonProcess app display-name=app_wsgi
Unfortunately, I get an Error 404. The debug information, though, is pretty mysterious. If I try to get www.example.com/app/myurl/, Django says
Using the URLconf defined in apps.urls, Django tried these URL patterns, in this order:
^myurl/$
...
The current URL, myurl/, didn't match any of these.
It seems that Django - correctly - infers that the path requested is myurl/, and not app/myurl/. But, even though myurl/ clearly matches ^myurl/$, it does not find a match.
I have also tried to add the setting
FORCE_SCRIPT_NAME = '/app'
but nothing changes - the error message remains identical.
The debug information lies :-/ Trying with more permissive regexs in the URL conf; iwas able to get a page. From there I could print request.path, and it turned out to be app/myurl/.
To make it work, I had instead to put
FORCE_SCRIPT_NAME = ''
STATIC_URL = '/app/static/'
MEDIA_URL = '/app/media/'