Revision 28adfa0f

/dev/null
1
Copyright 2011-2012 GRNET S.A. All rights reserved.
2

  
3
Redistribution and use in source and binary forms, with or
4
without modification, are permitted provided that the following
5
conditions are met:
6

  
7
  1. Redistributions of source code must retain the above
8
     copyright notice, this list of conditions and the following
9
     disclaimer.
10

  
11
  2. Redistributions in binary form must reproduce the above
12
     copyright notice, this list of conditions and the following
13
     disclaimer in the documentation and/or other materials
14
     provided with the distribution.
15

  
16
THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
POSSIBILITY OF SUCH DAMAGE.
28

  
29
The views and conclusions contained in the software and
30
documentation are those of the authors and should not be
31
interpreted as representing official policies, either expressed
32
or implied, of GRNET S.A.
/dev/null
1
Changelog
2
=========
3

  
4

  
5
v0.8.5
6
------
7

  
8
- Django app to serve the index.html
9
- Use synnefo.lib.context_processors.cloudbar to display cloudbar
10

  
/dev/null
1
include README Changelog
2
include distribute_setup.py
3
global-include */templates/* */fixtures/* */static/*
4
global-exclude */.DS_Store
5
recursive-include pithos_web_client/templates/ *.html *.txt
6
recursive-include pithos_web_client/static/ *.js *.css *.less *.html *.txt *.png *.gif *.jpg
7
prune docs
8
prune other
/dev/null
1
snf-pithos-web-client
2
=====================
3

  
4
This is the python package of the synnefo pithos ui frontend
5
webapp. It consist of a django application module which includes
6
a prebuilt version of the pithos ui gwt project contained in
7
`../src` directory.
8

  
9
The gwt built files are not included in the repository. Ant
10
hooks has been added in setup.py so that each time you run ``python
11
setup.py {develop, install, sdist}`` ant build is executed and
12
compiled js and other asset files are placed in the appropriate
13
locations within the python module to be packaged/installed.
14

  
/dev/null
1
# cloudbar configuration
2
#CLOUDBAR_ACTIVE = True
3
#CLOUDBAR_LOCATION = 'https://accounts.okeanos.grnet.gr/static/im/cloudbar/'
4
#CLOUDBAR_COOKIE_NAME = '_pithos2_a'
5
#CLOUDBAR_ACTIVE_SERVICE = 'cloud'
6
#CLOUDBAR_SERVICES_URL = 'https://accounts.okeanos.grnet.gr/im/get_services'
7
#CLOUDBAR_MENU_URL = 'https://accounts.okeanos.grnet.gr/im/get_menu'
8

  
/dev/null
1
# loginUrl MUST end at "next=". You should not give the value of the next
2
# parameter. It will be determined automatically
3
#PITHOS_UI_LOGIN_URL = "https://accounts.okeanos.grnet.gr/im/login?next="
4

  
5
# Feedback url
6
#PITHOS_UI_FEEDBACK_URL = "https://accounts.okeanos.grnet.gr/im/feedback"
7

  
8
# Cookie name to check if user is authenticated, this should match your astakos
9
# deployment cookie name
10
#PITHOS_UI_AUTH_COOKIE_NAME = "_pithos2_a"
/dev/null
1
#!python
2
"""Bootstrap distribute installation
3

  
4
If you want to use setuptools in your package's setup.py, just include this
5
file in the same directory with it, and add this to the top of your setup.py::
6

  
7
    from distribute_setup import use_setuptools
8
    use_setuptools()
9

  
10
If you want to require a specific version of setuptools, set a download
11
mirror, or use an alternate download directory, you can do so by supplying
12
the appropriate options to ``use_setuptools()``.
13

  
14
This file can also be run as a script to install or upgrade setuptools.
15
"""
16
import os
17
import sys
18
import time
19
import fnmatch
20
import tempfile
21
import tarfile
22
from distutils import log
23

  
24
try:
25
    from site import USER_SITE
26
except ImportError:
27
    USER_SITE = None
28

  
29
try:
30
    import subprocess
31

  
32
    def _python_cmd(*args):
33
        args = (sys.executable,) + args
34
        return subprocess.call(args) == 0
35

  
36
except ImportError:
37
    # will be used for python 2.3
38
    def _python_cmd(*args):
39
        args = (sys.executable,) + args
40
        # quoting arguments if windows
41
        if sys.platform == 'win32':
42
            def quote(arg):
43
                if ' ' in arg:
44
                    return '"%s"' % arg
45
                return arg
46
            args = [quote(arg) for arg in args]
47
        return os.spawnl(os.P_WAIT, sys.executable, *args) == 0
48

  
49
DEFAULT_VERSION = "0.6.10"
50
DEFAULT_URL = "http://pypi.python.org/packages/source/d/distribute/"
51
SETUPTOOLS_FAKED_VERSION = "0.6c11"
52

  
53
SETUPTOOLS_PKG_INFO = """\
54
Metadata-Version: 1.0
55
Name: setuptools
56
Version: %s
57
Summary: xxxx
58
Home-page: xxx
59
Author: xxx
60
Author-email: xxx
61
License: xxx
62
Description: xxx
63
""" % SETUPTOOLS_FAKED_VERSION
64

  
65

  
66
def _install(tarball):
67
    # extracting the tarball
68
    tmpdir = tempfile.mkdtemp()
69
    log.warn('Extracting in %s', tmpdir)
70
    old_wd = os.getcwd()
71
    try:
72
        os.chdir(tmpdir)
73
        tar = tarfile.open(tarball)
74
        _extractall(tar)
75
        tar.close()
76

  
77
        # going in the directory
78
        subdir = os.path.join(tmpdir, os.listdir(tmpdir)[0])
79
        os.chdir(subdir)
80
        log.warn('Now working in %s', subdir)
81

  
82
        # installing
83
        log.warn('Installing Distribute')
84
        if not _python_cmd('setup.py', 'install'):
85
            log.warn('Something went wrong during the installation.')
86
            log.warn('See the error message above.')
87
    finally:
88
        os.chdir(old_wd)
89

  
90

  
91
def _build_egg(egg, tarball, to_dir):
92
    # extracting the tarball
93
    tmpdir = tempfile.mkdtemp()
94
    log.warn('Extracting in %s', tmpdir)
95
    old_wd = os.getcwd()
96
    try:
97
        os.chdir(tmpdir)
98
        tar = tarfile.open(tarball)
99
        _extractall(tar)
100
        tar.close()
101

  
102
        # going in the directory
103
        subdir = os.path.join(tmpdir, os.listdir(tmpdir)[0])
104
        os.chdir(subdir)
105
        log.warn('Now working in %s', subdir)
106

  
107
        # building an egg
108
        log.warn('Building a Distribute egg in %s', to_dir)
109
        _python_cmd('setup.py', '-q', 'bdist_egg', '--dist-dir', to_dir)
110

  
111
    finally:
112
        os.chdir(old_wd)
113
    # returning the result
114
    log.warn(egg)
115
    if not os.path.exists(egg):
116
        raise IOError('Could not build the egg.')
117

  
118

  
119
def _do_download(version, download_base, to_dir, download_delay):
120
    egg = os.path.join(to_dir, 'distribute-%s-py%d.%d.egg'
121
                       % (version, sys.version_info[0], sys.version_info[1]))
122
    if not os.path.exists(egg):
123
        tarball = download_setuptools(version, download_base,
124
                                      to_dir, download_delay)
125
        _build_egg(egg, tarball, to_dir)
126
    sys.path.insert(0, egg)
127
    import setuptools
128
    setuptools.bootstrap_install_from = egg
129

  
130

  
131
def use_setuptools(version=DEFAULT_VERSION, download_base=DEFAULT_URL,
132
                   to_dir=os.curdir, download_delay=15, no_fake=True):
133
    # making sure we use the absolute path
134
    to_dir = os.path.abspath(to_dir)
135
    was_imported = 'pkg_resources' in sys.modules or \
136
        'setuptools' in sys.modules
137
    try:
138
        try:
139
            import pkg_resources
140
            if not hasattr(pkg_resources, '_distribute'):
141
                if not no_fake:
142
                    _fake_setuptools()
143
                raise ImportError
144
        except ImportError:
145
            return _do_download(version, download_base, to_dir, download_delay)
146
        try:
147
            pkg_resources.require("distribute>="+version)
148
            return
149
        except pkg_resources.VersionConflict:
150
            e = sys.exc_info()[1]
151
            if was_imported:
152
                sys.stderr.write(
153
                "The required version of distribute (>=%s) is not available,\n"
154
                "and can't be installed while this script is running. Please\n"
155
                "install a more recent version first, using\n"
156
                "'easy_install -U distribute'."
157
                "\n\n(Currently using %r)\n" % (version, e.args[0]))
158
                sys.exit(2)
159
            else:
160
                del pkg_resources, sys.modules['pkg_resources']    # reload ok
161
                return _do_download(version, download_base, to_dir,
162
                                    download_delay)
163
        except pkg_resources.DistributionNotFound:
164
            return _do_download(version, download_base, to_dir,
165
                                download_delay)
166
    finally:
167
        if not no_fake:
168
            _create_fake_setuptools_pkg_info(to_dir)
169

  
170
def download_setuptools(version=DEFAULT_VERSION, download_base=DEFAULT_URL,
171
                        to_dir=os.curdir, delay=15):
172
    """Download distribute from a specified location and return its filename
173

  
174
    `version` should be a valid distribute version number that is available
175
    as an egg for download under the `download_base` URL (which should end
176
    with a '/'). `to_dir` is the directory where the egg will be downloaded.
177
    `delay` is the number of seconds to pause before an actual download
178
    attempt.
179
    """
180
    # making sure we use the absolute path
181
    to_dir = os.path.abspath(to_dir)
182
    try:
183
        from urllib.request import urlopen
184
    except ImportError:
185
        from urllib2 import urlopen
186
    tgz_name = "distribute-%s.tar.gz" % version
187
    url = download_base + tgz_name
188
    saveto = os.path.join(to_dir, tgz_name)
189
    src = dst = None
190
    if not os.path.exists(saveto):  # Avoid repeated downloads
191
        try:
192
            log.warn("Downloading %s", url)
193
            src = urlopen(url)
194
            # Read/write all in one block, so we don't create a corrupt file
195
            # if the download is interrupted.
196
            data = src.read()
197
            dst = open(saveto, "wb")
198
            dst.write(data)
199
        finally:
200
            if src:
201
                src.close()
202
            if dst:
203
                dst.close()
204
    return os.path.realpath(saveto)
205

  
206
def _no_sandbox(function):
207
    def __no_sandbox(*args, **kw):
208
        try:
209
            from setuptools.sandbox import DirectorySandbox
210
            if not hasattr(DirectorySandbox, '_old'):
211
                def violation(*args):
212
                    pass
213
                DirectorySandbox._old = DirectorySandbox._violation
214
                DirectorySandbox._violation = violation
215
                patched = True
216
            else:
217
                patched = False
218
        except ImportError:
219
            patched = False
220

  
221
        try:
222
            return function(*args, **kw)
223
        finally:
224
            if patched:
225
                DirectorySandbox._violation = DirectorySandbox._old
226
                del DirectorySandbox._old
227

  
228
    return __no_sandbox
229

  
230
def _patch_file(path, content):
231
    """Will backup the file then patch it"""
232
    existing_content = open(path).read()
233
    if existing_content == content:
234
        # already patched
235
        log.warn('Already patched.')
236
        return False
237
    log.warn('Patching...')
238
    _rename_path(path)
239
    f = open(path, 'w')
240
    try:
241
        f.write(content)
242
    finally:
243
        f.close()
244
    return True
245

  
246
_patch_file = _no_sandbox(_patch_file)
247

  
248
def _same_content(path, content):
249
    return open(path).read() == content
250

  
251
def _rename_path(path):
252
    new_name = path + '.OLD.%s' % time.time()
253
    log.warn('Renaming %s into %s', path, new_name)
254
    os.rename(path, new_name)
255
    return new_name
256

  
257
def _remove_flat_installation(placeholder):
258
    if not os.path.isdir(placeholder):
259
        log.warn('Unkown installation at %s', placeholder)
260
        return False
261
    found = False
262
    for file in os.listdir(placeholder):
263
        if fnmatch.fnmatch(file, 'setuptools*.egg-info'):
264
            found = True
265
            break
266
    if not found:
267
        log.warn('Could not locate setuptools*.egg-info')
268
        return
269

  
270
    log.warn('Removing elements out of the way...')
271
    pkg_info = os.path.join(placeholder, file)
272
    if os.path.isdir(pkg_info):
273
        patched = _patch_egg_dir(pkg_info)
274
    else:
275
        patched = _patch_file(pkg_info, SETUPTOOLS_PKG_INFO)
276

  
277
    if not patched:
278
        log.warn('%s already patched.', pkg_info)
279
        return False
280
    # now let's move the files out of the way
281
    for element in ('setuptools', 'pkg_resources.py', 'site.py'):
282
        element = os.path.join(placeholder, element)
283
        if os.path.exists(element):
284
            _rename_path(element)
285
        else:
286
            log.warn('Could not find the %s element of the '
287
                     'Setuptools distribution', element)
288
    return True
289

  
290
_remove_flat_installation = _no_sandbox(_remove_flat_installation)
291

  
292
def _after_install(dist):
293
    log.warn('After install bootstrap.')
294
    placeholder = dist.get_command_obj('install').install_purelib
295
    _create_fake_setuptools_pkg_info(placeholder)
296

  
297
def _create_fake_setuptools_pkg_info(placeholder):
298
    if not placeholder or not os.path.exists(placeholder):
299
        log.warn('Could not find the install location')
300
        return
301
    pyver = '%s.%s' % (sys.version_info[0], sys.version_info[1])
302
    setuptools_file = 'setuptools-%s-py%s.egg-info' % \
303
            (SETUPTOOLS_FAKED_VERSION, pyver)
304
    pkg_info = os.path.join(placeholder, setuptools_file)
305
    if os.path.exists(pkg_info):
306
        log.warn('%s already exists', pkg_info)
307
        return
308

  
309
    log.warn('Creating %s', pkg_info)
310
    f = open(pkg_info, 'w')
311
    try:
312
        f.write(SETUPTOOLS_PKG_INFO)
313
    finally:
314
        f.close()
315

  
316
    pth_file = os.path.join(placeholder, 'setuptools.pth')
317
    log.warn('Creating %s', pth_file)
318
    f = open(pth_file, 'w')
319
    try:
320
        f.write(os.path.join(os.curdir, setuptools_file))
321
    finally:
322
        f.close()
323

  
324
_create_fake_setuptools_pkg_info = _no_sandbox(_create_fake_setuptools_pkg_info)
325

  
326
def _patch_egg_dir(path):
327
    # let's check if it's already patched
328
    pkg_info = os.path.join(path, 'EGG-INFO', 'PKG-INFO')
329
    if os.path.exists(pkg_info):
330
        if _same_content(pkg_info, SETUPTOOLS_PKG_INFO):
331
            log.warn('%s already patched.', pkg_info)
332
            return False
333
    _rename_path(path)
334
    os.mkdir(path)
335
    os.mkdir(os.path.join(path, 'EGG-INFO'))
336
    pkg_info = os.path.join(path, 'EGG-INFO', 'PKG-INFO')
337
    f = open(pkg_info, 'w')
338
    try:
339
        f.write(SETUPTOOLS_PKG_INFO)
340
    finally:
341
        f.close()
342
    return True
343

  
344
_patch_egg_dir = _no_sandbox(_patch_egg_dir)
345

  
346
def _before_install():
347
    log.warn('Before install bootstrap.')
348
    _fake_setuptools()
349

  
350

  
351
def _under_prefix(location):
352
    if 'install' not in sys.argv:
353
        return True
354
    args = sys.argv[sys.argv.index('install')+1:]
355
    for index, arg in enumerate(args):
356
        for option in ('--root', '--prefix'):
357
            if arg.startswith('%s=' % option):
358
                top_dir = arg.split('root=')[-1]
359
                return location.startswith(top_dir)
360
            elif arg == option:
361
                if len(args) > index:
362
                    top_dir = args[index+1]
363
                    return location.startswith(top_dir)
364
        if arg == '--user' and USER_SITE is not None:
365
            return location.startswith(USER_SITE)
366
    return True
367

  
368

  
369
def _fake_setuptools():
370
    log.warn('Scanning installed packages')
371
    try:
372
        import pkg_resources
373
    except ImportError:
374
        # we're cool
375
        log.warn('Setuptools or Distribute does not seem to be installed.')
376
        return
377
    ws = pkg_resources.working_set
378
    try:
379
        setuptools_dist = ws.find(pkg_resources.Requirement.parse('setuptools',
380
                                  replacement=False))
381
    except TypeError:
382
        # old distribute API
383
        setuptools_dist = ws.find(pkg_resources.Requirement.parse('setuptools'))
384

  
385
    if setuptools_dist is None:
386
        log.warn('No setuptools distribution found')
387
        return
388
    # detecting if it was already faked
389
    setuptools_location = setuptools_dist.location
390
    log.warn('Setuptools installation detected at %s', setuptools_location)
391

  
392
    # if --root or --preix was provided, and if
393
    # setuptools is not located in them, we don't patch it
394
    if not _under_prefix(setuptools_location):
395
        log.warn('Not patching, --root or --prefix is installing Distribute'
396
                 ' in another location')
397
        return
398

  
399
    # let's see if its an egg
400
    if not setuptools_location.endswith('.egg'):
401
        log.warn('Non-egg installation')
402
        res = _remove_flat_installation(setuptools_location)
403
        if not res:
404
            return
405
    else:
406
        log.warn('Egg installation')
407
        pkg_info = os.path.join(setuptools_location, 'EGG-INFO', 'PKG-INFO')
408
        if (os.path.exists(pkg_info) and
409
            _same_content(pkg_info, SETUPTOOLS_PKG_INFO)):
410
            log.warn('Already patched.')
411
            return
412
        log.warn('Patching...')
413
        # let's create a fake egg replacing setuptools one
414
        res = _patch_egg_dir(setuptools_location)
415
        if not res:
416
            return
417
    log.warn('Patched done.')
418
    _relaunch()
419

  
420

  
421
def _relaunch():
422
    log.warn('Relaunching...')
423
    # we have to relaunch the process
424
    # pip marker to avoid a relaunch bug
425
    if sys.argv[:3] == ['-c', 'install', '--single-version-externally-managed']:
426
        sys.argv[0] = 'setup.py'
427
    args = [sys.executable] + sys.argv
428
    sys.exit(subprocess.call(args))
429

  
430

  
431
def _extractall(self, path=".", members=None):
432
    """Extract all members from the archive to the current working
433
       directory and set owner, modification time and permissions on
434
       directories afterwards. `path' specifies a different directory
435
       to extract to. `members' is optional and must be a subset of the
436
       list returned by getmembers().
437
    """
438
    import copy
439
    import operator
440
    from tarfile import ExtractError
441
    directories = []
442

  
443
    if members is None:
444
        members = self
445

  
446
    for tarinfo in members:
447
        if tarinfo.isdir():
448
            # Extract directories with a safe mode.
449
            directories.append(tarinfo)
450
            tarinfo = copy.copy(tarinfo)
451
            tarinfo.mode = 448 # decimal for oct 0700
452
        self.extract(tarinfo, path)
453

  
454
    # Reverse sort directories.
455
    if sys.version_info < (2, 4):
456
        def sorter(dir1, dir2):
457
            return cmp(dir1.name, dir2.name)
458
        directories.sort(sorter)
459
        directories.reverse()
460
    else:
461
        directories.sort(key=operator.attrgetter('name'), reverse=True)
462

  
463
    # Set correct owner, mtime and filemode on directories.
464
    for tarinfo in directories:
465
        dirpath = os.path.join(path, tarinfo.name)
466
        try:
467
            self.chown(tarinfo, dirpath)
468
            self.utime(tarinfo, dirpath)
469
            self.chmod(tarinfo, dirpath)
470
        except ExtractError:
471
            e = sys.exc_info()[1]
472
            if self.errorlevel > 1:
473
                raise
474
            else:
475
                self._dbg(1, "tarfile: %s" % e)
476

  
477

  
478
def main(argv, version=DEFAULT_VERSION):
479
    """Install or upgrade setuptools and EasyInstall"""
480
    tarball = download_setuptools()
481
    _install(tarball)
482

  
483

  
484
if __name__ == '__main__':
485
    main(sys.argv[1:])
/dev/null
1
from django.conf import settings
2

  
3
# !!!!!ATTENTION!!!!!
4
# loginUrl MUST end at "next=". You should not give the value of the next
5
# parameter. It will be determined automatically
6
LOGIN_URL = getattr(settings, 'PITHOS_UI_LOGIN_URL', 'https://accounts.okeanos.grnet.gr/im/login?next=')
7
FEEDBACK_URL = getattr(settings, 'PITHOS_UI_FEEDBACK_URL', 'https://accounts.okeanos.grnet.gr/im/feedback')
8
AUTH_COOKIE_NAME = getattr(settings, 'PITHOS_UI_AUTH_COOKIE_NAME', '_pithos2_a')
9

  
/dev/null
1
# Copyright 2011-2012 GRNET S.A. All rights reserved.
2
#
3
# Redistribution and use in source and binary forms, with or
4
# without modification, are permitted provided that the following
5
# conditions are met:
6
#
7
#   1. Redistributions of source code must retain the above
8
#      copyright notice, this list of conditions and the following
9
#      disclaimer.
10
#
11
#   2. Redistributions in binary form must reproduce the above
12
#      copyright notice, this list of conditions and the following
13
#      disclaimer in the documentation and/or other materials
14
#      provided with the distribution.
15
#
16
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
# POSSIBILITY OF SUCH DAMAGE.
28
#
29
# The views and conclusions contained in the software and
30
# documentation are those of the authors and should not be
31
# interpreted as representing official policies, either expressed
32
# or implied, of GRNET S.A.
33
#
34

  
35
"""
36
Django settings metadata. To be used in setup.py snf-webproject entry points.
37
"""
38

  
39
installed_apps = [
40
        'pithos_web_client'
41
]
42

  
43
static_files = {'pithos_web_client': ''}
44

  
45
context_processors = [
46
   'synnefo.lib.context_processors.cloudbar'
47
]
48

  
49
# namespace
50
from django.conf.urls.defaults import include, patterns
51
urlpatterns = patterns('',
52
    (r'^ui/$', 'pithos_web_client.views.index'),
53
    (r'^ui/index.html$', 'pithos_web_client.views.index'),
54
    (r'^pithos/ui/$', 'pithos_web_client.views.index'),
55
    (r'^pithos/ui/index.html$', 'pithos_web_client.views.index')
56
)
/dev/null
1
# Copyright 2011-2012 GRNET S.A. All rights reserved.
2
#
3
# Redistribution and use in source and binary forms, with or
4
# without modification, are permitted provided that the following
5
# conditions are met:
6
#
7
#   1. Redistributions of source code must retain the above
8
#      copyright notice, this list of conditions and the following
9
#      disclaimer.
10
#
11
#   2. Redistributions in binary form must reproduce the above
12
#      copyright notice, this list of conditions and the following
13
#      disclaimer in the documentation and/or other materials
14
#      provided with the distribution.
15
#
16
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
# POSSIBILITY OF SUCH DAMAGE.
28
#
29
# The views and conclusions contained in the software and
30
# documentation are those of the authors and should not be
31
# interpreted as representing official policies, either expressed
32
# or implied, of GRNET S.A.
33

  
34
from django.conf.urls.defaults import include, patterns
35

  
36

  
37
urlpatterns = patterns('',
38
    (r'^$', 'pithos_web_client.views.index')
39
)
40

  
/dev/null
1
# Copyright 2011-2012 GRNET S.A. All rights reserved.
2
#
3
# Redistribution and use in source and binary forms, with or
4
# without modification, are permitted provided that the following
5
# conditions are met:
6
#
7
#   1. Redistributions of source code must retain the above
8
#      copyright notice, this list of conditions and the following
9
#      disclaimer.
10
#
11
#   2. Redistributions in binary form must reproduce the above
12
#      copyright notice, this list of conditions and the following
13
#      disclaimer in the documentation and/or other materials
14
#      provided with the distribution.
15
#
16
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
# POSSIBILITY OF SUCH DAMAGE.
28
#
29
# The views and conclusions contained in the software and
30
# documentation are those of the authors and should not be
31
# interpreted as representing official policies, either expressed
32
# or implied, of GRNET S.A.
33

  
34
from django.views.generic.simple import direct_to_template
35

  
36
from pithos_web_client import settings
37
from django.conf import settings as django_settings
38

  
39
MEDIA_URL = getattr(settings, "PITHOS_WEB_CLIENT_MEDIA_URL", \
40
        getattr(django_settings, "MEDIA_URL", "/static/"))
41

  
42
def index(request):
43
    return direct_to_template(request, 'pithos_web_client/index.html', \
44
            {'settings': settings, 'MEDIA_URL': MEDIA_URL})
45

  
/dev/null
1
#!/usr/bin/env python
2

  
3
# Copyright 2011-2012 GRNET S.A. All rights reserved.
4
#
5
# Redistribution and use in source and binary forms, with or
6
# without modification, are permitted provided that the following
7
# conditions are met:
8
#
9
#   1. Redistributions of source code must retain the above
10
#      copyright notice, this list of conditions and the following
11
#      disclaimer.
12
#
13
#   2. Redistributions in binary form must reproduce the above
14
#      copyright notice, this list of conditions and the following
15
#      disclaimer in the documentation and/or other materials
16
#      provided with the distribution.
17
#
18
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
19
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
20
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
21
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
22
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
25
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
26
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
28
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
# POSSIBILITY OF SUCH DAMAGE.
30
#
31
# The views and conclusions contained in the software and
32
# documentation are those of the authors and should not be
33
# interpreted as representing official policies, either expressed
34
# or implied, of GRNET S.A.
35
import distribute_setup
36
distribute_setup.use_setuptools()
37

  
38
import os
39
import sys
40

  
41
from fnmatch import fnmatchcase
42
from distutils.util import convert_path
43

  
44
from setuptools import setup, find_packages
45

  
46

  
47
HERE = os.path.abspath(os.path.normpath(os.path.dirname(__file__)))
48
try:
49
    # try to update the version file
50
    from synnefo.util import version
51
    version.update_version('pithos_web_client', 'version', HERE)
52
except ImportError:
53
    pass
54

  
55
from pithos_web_client.version import __version__
56

  
57
# Package info
58
VERSION = __version__
59
README = open(os.path.join(HERE, 'README')).read()
60
CHANGES = open(os.path.join(HERE, 'Changelog')).read()
61
SHORT_DESCRIPTION = 'Package short description'
62

  
63
PACKAGES_ROOT = '.'
64
PACKAGES = find_packages(PACKAGES_ROOT)
65

  
66
# Package meta
67
CLASSIFIERS = [
68
        'Development Status :: 3 - Alpha',
69
        'Operating System :: OS Independent',
70
        'Programming Language :: Python',
71
        'Topic :: Utilities',
72
        'License :: OSI Approved :: BSD License',
73
]
74

  
75
# Package requirements
76
INSTALL_REQUIRES = [
77
    'Django>=1.2, <1.3',
78
    'snf-common>=0.9.0rc'
79
]
80

  
81
EXTRAS_REQUIRES = {
82
}
83

  
84
TESTS_REQUIRES = [
85
]
86

  
87
# Provided as an attribute, so you can append to these instead
88
# of replicating them:
89
standard_exclude = ["*.py", "*.pyc", "*$py.class", "*~", ".*", "*.bak"]
90
standard_exclude_directories = [
91
    ".*", "CVS", "_darcs", "./build", "./dist", "EGG-INFO", "*.egg-info", "snf-0.7"
92
]
93

  
94
# (c) 2005 Ian Bicking and contributors; written for Paste (http://pythonpaste.org)
95
# Licensed under the MIT license: http://www.opensource.org/licenses/mit-license.php
96
# Note: you may want to copy this into your setup.py file verbatim, as
97
# you can't import this from another package, when you don't know if
98
# that package is installed yet.
99
def find_package_data(
100
    where=".",
101
    package="",
102
    exclude=standard_exclude,
103
    exclude_directories=standard_exclude_directories,
104
    only_in_packages=True,
105
    show_ignored=False):
106
    """
107
    Return a dictionary suitable for use in ``package_data``
108
    in a distutils ``setup.py`` file.
109

  
110
    The dictionary looks like::
111

  
112
        {"package": [files]}
113

  
114
    Where ``files`` is a list of all the files in that package that
115
    don"t match anything in ``exclude``.
116

  
117
    If ``only_in_packages`` is true, then top-level directories that
118
    are not packages won"t be included (but directories under packages
119
    will).
120

  
121
    Directories matching any pattern in ``exclude_directories`` will
122
    be ignored; by default directories with leading ``.``, ``CVS``,
123
    and ``_darcs`` will be ignored.
124

  
125
    If ``show_ignored`` is true, then all the files that aren"t
126
    included in package data are shown on stderr (for debugging
127
    purposes).
128

  
129
    Note patterns use wildcards, or can be exact paths (including
130
    leading ``./``), and all searching is case-insensitive.
131
    """
132
    out = {}
133
    stack = [(convert_path(where), "", package, only_in_packages)]
134
    while stack:
135
        where, prefix, package, only_in_packages = stack.pop(0)
136
        for name in os.listdir(where):
137
            fn = os.path.join(where, name)
138
            if os.path.isdir(fn):
139
                bad_name = False
140
                for pattern in exclude_directories:
141
                    if (fnmatchcase(name, pattern)
142
                        or fn.lower() == pattern.lower()):
143
                        bad_name = True
144
                        if show_ignored:
145
                            print >> sys.stderr, (
146
                                "Directory %s ignored by pattern %s"
147
                                % (fn, pattern))
148
                        break
149
                if bad_name:
150
                    continue
151
                if (os.path.isfile(os.path.join(fn, "__init__.py"))
152
                    and not prefix):
153
                    if not package:
154
                        new_package = name
155
                    else:
156
                        new_package = package + "." + name
157
                    stack.append((fn, "", new_package, False))
158
                else:
159
                    stack.append((fn, prefix + name + "/", package, only_in_packages))
160
            elif package or not only_in_packages:
161
                # is a file
162
                bad_name = False
163
                for pattern in exclude:
164
                    if (fnmatchcase(name, pattern)
165
                        or fn.lower() == pattern.lower()):
166
                        bad_name = True
167
                        if show_ignored:
168
                            print >> sys.stderr, (
169
                                "File %s ignored by pattern %s"
170
                                % (fn, pattern))
171
                        break
172
                if bad_name:
173
                    continue
174
                out.setdefault(package, []).append(prefix+name)
175
    return out
176

  
177

  
178
"""
179
Gwt clea/build helpers
180
"""
181
import subprocess as sp
182
import glob
183

  
184
def clean_gwt(root="../", public_dir="bin/www/gr.grnet.pithos.web.Pithos/"):
185
    # skip if no build.xml found (debian build process)
186
    if not os.path.exists(os.path.join(root, "build.xml")):
187
        return
188

  
189
    curdir = os.getcwd()
190
    os.chdir(root)
191
    rcode = sp.call(["ant", "clean"])
192
    if rcode == 1:
193
        raise Exception("GWT clean failed")
194
    os.chdir(curdir)
195
    pub_dir = os.path.abspath(os.path.join(root, public_dir))
196
    static_dir = os.path.abspath(os.path.join("pithos_web_client", "static", \
197
        "pithos_web_client"))
198
    templates_dir = os.path.abspath(os.path.join("pithos_web_client", \
199
        "templates", "pithos_web_client"))
200
    clean_static = ["rm", "-r"] + glob.glob(os.path.join(static_dir, "*"))
201
    clean_templates = ["rm", "-r"] + glob.glob(os.path.join(templates_dir, "*"))
202

  
203
    # clean dirs
204
    if len(clean_static) > 2:
205
        sp.call(clean_static)
206
    if len(clean_static) > 2:
207
        sp.call(clean_templates)
208

  
209

  
210
def build_gwt(root="../", public_dir="bin/www/gr.grnet.pithos.web.Pithos/"):
211
    # skip if no build.xml found (debian build process)
212
    if not os.path.exists(os.path.join(root, "build.xml")):
213
        return
214

  
215
    curdir = os.getcwd()
216
    os.chdir(root)
217
    # run ant on root dir
218
    rcode = sp.call(["ant"])
219
    if rcode == 1:
220
        raise Exception("GWT build failed")
221
    os.chdir(curdir)
222

  
223

  
224
    pub_dir = os.path.abspath(os.path.join(root, public_dir))
225
    static_dir = os.path.abspath(os.path.join("pithos_web_client", "static", \
226
        "pithos_web_client"))
227
    templates_dir = os.path.abspath(os.path.join("pithos_web_client", \
228
        "templates", "pithos_web_client"))
229

  
230
    clean_static = ["rm", "-r"] + glob.glob(os.path.join(static_dir, "*"))
231
    clean_templates = ["rm", "-r"] + glob.glob(os.path.join(templates_dir, "*"))
232

  
233
    # clean dirs
234
    if len(clean_static) > 2:
235
        sp.call(clean_static)
236
    if len(clean_static) > 2:
237
        sp.call(clean_templates)
238

  
239
    copy_static = ["cp", "-r"] + glob.glob(os.path.join(pub_dir, "*")) + [static_dir]
240
    copy_index = ["cp", os.path.join(pub_dir, "index.html"), templates_dir]
241
    sp.call(copy_static)
242
    sp.call(copy_index)
243

  
244
    index = os.path.join(templates_dir, "index.html")
245
    index_data = file(index).read()
246
    index_data = index_data.replace('href="', 'href="{{ MEDIA_URL }}pithos_web_client/')
247
    index_data = index_data.replace('" src="', '" src="{{ MEDIA_URL }}pithos_web_client/')
248
    index_data = index_data.replace('\' src=\'', '\' src=\'{{ MEDIA_URL }}pithos_web_client/')
249
    index_data = index_data.replace('url(', 'url({{ MEDIA_URL }}pithos_web_client/')
250

  
251
    ifile = file(index, "w+")
252
    ifile.write(index_data)
253
    ifile.close()
254

  
255

  
256
# do we need to run ant ???
257
if any(x in ''.join(sys.argv) for x in ["sdist", "build", "develop", "install"]):
258
    build_gwt()
259

  
260
if any(x in ''.join(sys.argv) for x in ["clean"]):
261
    clean_gwt()
262

  
263

  
264
setup(
265
    name='snf-pithos-web-client',
266
    version=VERSION,
267
    license='BSD',
268
    url='http://code.grnet.gr/projects/pithos-web-client',
269
    description = SHORT_DESCRIPTION,
270
    long_description=README + '\n\n' +  CHANGES,
271
    classifiers = CLASSIFIERS,
272
    author='GRNET',
273
    author_email='pithos@grnet.gr',
274

  
275
    packages=find_packages(),
276
    include_package_data=True,
277
    package_data=find_package_data('.'),
278
    zip_safe=False,
279

  
280
    install_requires = INSTALL_REQUIRES,
281

  
282
    dependency_links = ['http://docs.dev.grnet.gr/pypi'],
283

  
284
    entry_points={
285
        'synnefo': [
286
             'web_apps = pithos_web_client.synnefo_settings:installed_apps',
287
             'urls = pithos_web_client.synnefo_settings:urlpatterns',
288
             'web_static = pithos_web_client.synnefo_settings:static_files',
289
             'web_context_processors = pithos_web_client.synnefo_settings:context_processors'
290
        ]
291
    }
292
)
293

  
b/snf-pithos-webclient/COPYRIGHT
1
Copyright 2011-2012 GRNET S.A. All rights reserved.
2

  
3
Redistribution and use in source and binary forms, with or
4
without modification, are permitted provided that the following
5
conditions are met:
6

  
7
  1. Redistributions of source code must retain the above
8
     copyright notice, this list of conditions and the following
9
     disclaimer.
10

  
11
  2. Redistributions in binary form must reproduce the above
12
     copyright notice, this list of conditions and the following
13
     disclaimer in the documentation and/or other materials
14
     provided with the distribution.
15

  
16
THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
POSSIBILITY OF SUCH DAMAGE.
28

  
29
The views and conclusions contained in the software and
30
documentation are those of the authors and should not be
31
interpreted as representing official policies, either expressed
32
or implied, of GRNET S.A.
b/snf-pithos-webclient/Changelog
1
Changelog
2
=========
3

  
4

  
5
v0.8.5
6
------
7

  
8
- Django app to serve the index.html
9
- Use synnefo.lib.context_processors.cloudbar to display cloudbar
10

  
b/snf-pithos-webclient/MANIFEST.in
1
include README Changelog
2
include distribute_setup.py
3
global-include */templates/* */fixtures/* */static/*
4
global-exclude */.DS_Store
5
recursive-include pithos_web_client/templates/ *.html *.txt
6
recursive-include pithos_web_client/static/ *.js *.css *.less *.html *.txt *.png *.gif *.jpg
7
prune docs
8
prune other
b/snf-pithos-webclient/README
1
snf-pithos-web-client
2
=====================
3

  
4
This is the python package of the synnefo pithos ui frontend
5
webapp. It consist of a django application module which includes
6
a prebuilt version of the pithos ui gwt project contained in
7
`../src` directory.
8

  
9
The gwt built files are not included in the repository. Ant
10
hooks has been added in setup.py so that each time you run ``python
11
setup.py {develop, install, sdist}`` ant build is executed and
12
compiled js and other asset files are placed in the appropriate
13
locations within the python module to be packaged/installed.
14

  
b/snf-pithos-webclient/conf/20-snf-pithos-webclient-cloudbar.conf
1
# cloudbar configuration
2
#CLOUDBAR_ACTIVE = True
3
#CLOUDBAR_LOCATION = 'https://accounts.okeanos.grnet.gr/static/im/cloudbar/'
4
#CLOUDBAR_COOKIE_NAME = '_pithos2_a'
5
#CLOUDBAR_ACTIVE_SERVICE = 'cloud'
6
#CLOUDBAR_SERVICES_URL = 'https://accounts.okeanos.grnet.gr/im/get_services'
7
#CLOUDBAR_MENU_URL = 'https://accounts.okeanos.grnet.gr/im/get_menu'
8

  
b/snf-pithos-webclient/conf/20-snf-pithos-webclient-settings.conf
1
# loginUrl MUST end at "next=". You should not give the value of the next
2
# parameter. It will be determined automatically
3
#PITHOS_UI_LOGIN_URL = "https://accounts.okeanos.grnet.gr/im/login?next="
4

  
5
# Feedback url
6
#PITHOS_UI_FEEDBACK_URL = "https://accounts.okeanos.grnet.gr/im/feedback"
7

  
8
# Cookie name to check if user is authenticated, this should match your astakos
9
# deployment cookie name
10
#PITHOS_UI_AUTH_COOKIE_NAME = "_pithos2_a"
b/snf-pithos-webclient/distribute_setup.py
1
#!python
2
"""Bootstrap distribute installation
3

  
4
If you want to use setuptools in your package's setup.py, just include this
5
file in the same directory with it, and add this to the top of your setup.py::
6

  
7
    from distribute_setup import use_setuptools
8
    use_setuptools()
9

  
10
If you want to require a specific version of setuptools, set a download
11
mirror, or use an alternate download directory, you can do so by supplying
12
the appropriate options to ``use_setuptools()``.
13

  
14
This file can also be run as a script to install or upgrade setuptools.
15
"""
16
import os
17
import sys
18
import time
19
import fnmatch
20
import tempfile
21
import tarfile
22
from distutils import log
23

  
24
try:
25
    from site import USER_SITE
26
except ImportError:
27
    USER_SITE = None
28

  
29
try:
30
    import subprocess
31

  
32
    def _python_cmd(*args):
33
        args = (sys.executable,) + args
34
        return subprocess.call(args) == 0
35

  
36
except ImportError:
37
    # will be used for python 2.3
38
    def _python_cmd(*args):
39
        args = (sys.executable,) + args
40
        # quoting arguments if windows
41
        if sys.platform == 'win32':
42
            def quote(arg):
43
                if ' ' in arg:
44
                    return '"%s"' % arg
45
                return arg
46
            args = [quote(arg) for arg in args]
47
        return os.spawnl(os.P_WAIT, sys.executable, *args) == 0
48

  
49
DEFAULT_VERSION = "0.6.10"
50
DEFAULT_URL = "http://pypi.python.org/packages/source/d/distribute/"
51
SETUPTOOLS_FAKED_VERSION = "0.6c11"
52

  
53
SETUPTOOLS_PKG_INFO = """\
54
Metadata-Version: 1.0
55
Name: setuptools
56
Version: %s
57
Summary: xxxx
58
Home-page: xxx
59
Author: xxx
60
Author-email: xxx
61
License: xxx
62
Description: xxx
63
""" % SETUPTOOLS_FAKED_VERSION
64

  
65

  
66
def _install(tarball):
67
    # extracting the tarball
68
    tmpdir = tempfile.mkdtemp()
69
    log.warn('Extracting in %s', tmpdir)
70
    old_wd = os.getcwd()
71
    try:
72
        os.chdir(tmpdir)
73
        tar = tarfile.open(tarball)
74
        _extractall(tar)
75
        tar.close()
76

  
77
        # going in the directory
78
        subdir = os.path.join(tmpdir, os.listdir(tmpdir)[0])
79
        os.chdir(subdir)
80
        log.warn('Now working in %s', subdir)
81

  
82
        # installing
83
        log.warn('Installing Distribute')
84
        if not _python_cmd('setup.py', 'install'):
85
            log.warn('Something went wrong during the installation.')
86
            log.warn('See the error message above.')
87
    finally:
88
        os.chdir(old_wd)
89

  
90

  
91
def _build_egg(egg, tarball, to_dir):
92
    # extracting the tarball
93
    tmpdir = tempfile.mkdtemp()
94
    log.warn('Extracting in %s', tmpdir)
95
    old_wd = os.getcwd()
96
    try:
97
        os.chdir(tmpdir)
98
        tar = tarfile.open(tarball)
99
        _extractall(tar)
100
        tar.close()
101

  
102
        # going in the directory
103
        subdir = os.path.join(tmpdir, os.listdir(tmpdir)[0])
104
        os.chdir(subdir)
105
        log.warn('Now working in %s', subdir)
106

  
107
        # building an egg
108
        log.warn('Building a Distribute egg in %s', to_dir)
109
        _python_cmd('setup.py', '-q', 'bdist_egg', '--dist-dir', to_dir)
110

  
111
    finally:
112
        os.chdir(old_wd)
113
    # returning the result
114
    log.warn(egg)
115
    if not os.path.exists(egg):
116
        raise IOError('Could not build the egg.')
117

  
118

  
119
def _do_download(version, download_base, to_dir, download_delay):
120
    egg = os.path.join(to_dir, 'distribute-%s-py%d.%d.egg'
121
                       % (version, sys.version_info[0], sys.version_info[1]))
122
    if not os.path.exists(egg):
123
        tarball = download_setuptools(version, download_base,
124
                                      to_dir, download_delay)
125
        _build_egg(egg, tarball, to_dir)
126
    sys.path.insert(0, egg)
127
    import setuptools
128
    setuptools.bootstrap_install_from = egg
129

  
130

  
131
def use_setuptools(version=DEFAULT_VERSION, download_base=DEFAULT_URL,
132
                   to_dir=os.curdir, download_delay=15, no_fake=True):
133
    # making sure we use the absolute path
134
    to_dir = os.path.abspath(to_dir)
135
    was_imported = 'pkg_resources' in sys.modules or \
136
        'setuptools' in sys.modules
137
    try:
138
        try:
139
            import pkg_resources
140
            if not hasattr(pkg_resources, '_distribute'):
141
                if not no_fake:
142
                    _fake_setuptools()
143
                raise ImportError
144
        except ImportError:
145
            return _do_download(version, download_base, to_dir, download_delay)
146
        try:
147
            pkg_resources.require("distribute>="+version)
148
            return
149
        except pkg_resources.VersionConflict:
150
            e = sys.exc_info()[1]
151
            if was_imported:
152
                sys.stderr.write(
153
                "The required version of distribute (>=%s) is not available,\n"
154
                "and can't be installed while this script is running. Please\n"
155
                "install a more recent version first, using\n"
156
                "'easy_install -U distribute'."
157
                "\n\n(Currently using %r)\n" % (version, e.args[0]))
158
                sys.exit(2)
159
            else:
160
                del pkg_resources, sys.modules['pkg_resources']    # reload ok
161
                return _do_download(version, download_base, to_dir,
162
                                    download_delay)
163
        except pkg_resources.DistributionNotFound:
164
            return _do_download(version, download_base, to_dir,
165
                                download_delay)
166
    finally:
167
        if not no_fake:
168
            _create_fake_setuptools_pkg_info(to_dir)
169

  
170
def download_setuptools(version=DEFAULT_VERSION, download_base=DEFAULT_URL,
171
                        to_dir=os.curdir, delay=15):
172
    """Download distribute from a specified location and return its filename
173

  
174
    `version` should be a valid distribute version number that is available
175
    as an egg for download under the `download_base` URL (which should end
176
    with a '/'). `to_dir` is the directory where the egg will be downloaded.
177
    `delay` is the number of seconds to pause before an actual download
178
    attempt.
179
    """
180
    # making sure we use the absolute path
181
    to_dir = os.path.abspath(to_dir)
182
    try:
183
        from urllib.request import urlopen
184
    except ImportError:
185
        from urllib2 import urlopen
186
    tgz_name = "distribute-%s.tar.gz" % version
187
    url = download_base + tgz_name
188
    saveto = os.path.join(to_dir, tgz_name)
189
    src = dst = None
190
    if not os.path.exists(saveto):  # Avoid repeated downloads
191
        try:
192
            log.warn("Downloading %s", url)
193
            src = urlopen(url)
194
            # Read/write all in one block, so we don't create a corrupt file
195
            # if the download is interrupted.
196
            data = src.read()
197
            dst = open(saveto, "wb")
198
            dst.write(data)
199
        finally:
200
            if src:
201
                src.close()
202
            if dst:
203
                dst.close()
204
    return os.path.realpath(saveto)
205

  
206
def _no_sandbox(function):
207
    def __no_sandbox(*args, **kw):
208
        try:
209
            from setuptools.sandbox import DirectorySandbox
210
            if not hasattr(DirectorySandbox, '_old'):
211
                def violation(*args):
212
                    pass
213
                DirectorySandbox._old = DirectorySandbox._violation
214
                DirectorySandbox._violation = violation
215
                patched = True
216
            else:
217
                patched = False
218
        except ImportError:
219
            patched = False
220

  
221
        try:
222
            return function(*args, **kw)
223
        finally:
224
            if patched:
225
                DirectorySandbox._violation = DirectorySandbox._old
226
                del DirectorySandbox._old
227

  
228
    return __no_sandbox
229

  
230
def _patch_file(path, content):
231
    """Will backup the file then patch it"""
232
    existing_content = open(path).read()
233
    if existing_content == content:
234
        # already patched
235
        log.warn('Already patched.')
236
        return False
237
    log.warn('Patching...')
238
    _rename_path(path)
239
    f = open(path, 'w')
240
    try:
241
        f.write(content)
242
    finally:
243
        f.close()
244
    return True
245

  
246
_patch_file = _no_sandbox(_patch_file)
247

  
248
def _same_content(path, content):
249
    return open(path).read() == content
250

  
251
def _rename_path(path):
252
    new_name = path + '.OLD.%s' % time.time()
253
    log.warn('Renaming %s into %s', path, new_name)
254
    os.rename(path, new_name)
255
    return new_name
256

  
257
def _remove_flat_installation(placeholder):
258
    if not os.path.isdir(placeholder):
259
        log.warn('Unkown installation at %s', placeholder)
260
        return False
261
    found = False
262
    for file in os.listdir(placeholder):
263
        if fnmatch.fnmatch(file, 'setuptools*.egg-info'):
264
            found = True
265
            break
266
    if not found:
267
        log.warn('Could not locate setuptools*.egg-info')
268
        return
269

  
270
    log.warn('Removing elements out of the way...')
271
    pkg_info = os.path.join(placeholder, file)
272
    if os.path.isdir(pkg_info):
273
        patched = _patch_egg_dir(pkg_info)
274
    else:
275
        patched = _patch_file(pkg_info, SETUPTOOLS_PKG_INFO)
276

  
277
    if not patched:
... This diff was truncated because it exceeds the maximum size that can be displayed.

Also available in: Unified diff