1
+ import os .path
2
+ import inspect
3
+
4
+ import django .conf
1
5
from django .core .files .storage import FileSystemStorage
2
6
from django .core .files .storage import get_storage_class
7
+ from django .core .files import File
3
8
4
9
from compressor .conf import settings
5
10
@@ -18,3 +23,79 @@ def __init__(self, location=None, base_url=None, *args, **kwargs):
18
23
base_url = settings .MEDIA_URL
19
24
super (CompressorFileStorage , self ).__init__ (location , base_url ,
20
25
* args , ** kwargs )
26
+
27
+ class AppSavvyCompressorFileStorage (CompressorFileStorage ):
28
+ """
29
+ App Based file system storage for files handled by django-compressor.
30
+
31
+ This storage tries to use the project's media path first. If not found,
32
+ then it will try every installed app (in app reverse order, as to respect
33
+ app precedence). If none found it returns false.
34
+
35
+ The defaults for ``location`` and ``base_url`` are ``COMPRESS_ROOT`` and
36
+ ``COMPRESS_URL``.
37
+
38
+ """
39
+ def __init__ (self , location = None , base_url = None , * args , ** kwargs ):
40
+ if location is None :
41
+ location = settings .MEDIA_ROOT
42
+ if base_url is None :
43
+ base_url = settings .MEDIA_URL
44
+ super (AppSavvyCompressorFileStorage , self ).__init__ (location ,
45
+ base_url ,
46
+ * args ,
47
+ ** kwargs )
48
+
49
+ def _open (self , name , mode = 'rb' ):
50
+ if os .path .exists (os .path .join (self .location , name )):
51
+ return super (AppSavvyCompressorFileStorage , self ) \
52
+ ._open (name , mode )
53
+
54
+ paths = self .get_media_paths ()
55
+ for app , media_path in paths :
56
+ file_path = os .path .join (media_path , name )
57
+ if os .path .exists (file_path ):
58
+ return File (open (file_path , mode ))
59
+
60
+ raise ValueError ('The file with name %s could not be found in the project MEDIA_ROOT or any of the installed apps media folders.' % name )
61
+
62
+ def source_path (self , name ):
63
+ if os .path .exists (os .path .join (self .location , name )):
64
+ return os .path .join (self .location , name )
65
+
66
+ paths = self .get_media_paths ()
67
+ for app , media_path in paths :
68
+ file_path = os .path .join (media_path , name )
69
+ if os .path .exists (file_path ):
70
+ return file_path
71
+
72
+ def exists (self , name ):
73
+ if os .path .exists (os .path .join (self .location , name )):
74
+ return True
75
+
76
+ paths = self .get_media_paths ()
77
+
78
+ try :
79
+ for app , media_path in paths :
80
+ if os .path .exists (os .path .join (media_path , name )):
81
+ return True
82
+
83
+ return False
84
+ except Exception , err :
85
+ import pdb ;pdb .set_trace ()
86
+
87
+ def get_media_paths (self ):
88
+ paths = []
89
+ for app in reversed (django .conf .settings .INSTALLED_APPS ):
90
+ module = self .import_app (app )
91
+ module_path = os .path .dirname (inspect .getfile (module ))
92
+ media_path = os .path .join (module_path , 'media' )
93
+ paths .append ((app , media_path ))
94
+ return paths
95
+
96
+ def import_app (self , appname ):
97
+ main_module = __import__ (appname )
98
+ if not "." in appname :
99
+ return main_module
100
+
101
+ return reduce (getattr , appname .split ('.' )[1 :], main_module )
0 commit comments