##// END OF EJS Templates
release: Merge default into stable for release preparation
marcink -
r3786:3da01d04 merge stable
parent child Browse files
Show More
@@ -0,0 +1,28 b''
1 .. _repo-admin-set:
2 .. _permissions-info-add-group-ref:
3
4 Repository Administration
5 =========================
6
7 Repository permissions in |RCE| can be managed in a number of different ways.
8 This overview should give you an insight into how you could adopt particular
9 settings for your needs:
10
11 * Global |repo| permissions: This allows you to set the default permissions
12 for each new |repo| created within |RCE|, see :ref:`repo-default-ref`. All
13 |repos| created will inherit these permissions unless explicitly configured.
14 * Individual |repo| permissions: To set individual |repo| permissions,
15 see :ref:`set-repo-perms`.
16 * Repository Group permissions: This allows you to define the permissions for
17 a group, and all |repos| created within that group will inherit the same
18 permissions.
19
20 .. toctree::
21
22 repo_admin/repo-perm-steps
23 repo_admin/repo-extra-fields
24 repo_admin/repo-hooks
25 repo_admin/repo-issue-tracker
26 repo_admin/repo-vcs
27 repo_admin/restore-deleted-repositories
28 repo_admin/repo-admin-tasks No newline at end of file
@@ -0,0 +1,24 b''
1 .. _repo-admin-tasks:
2
3 Common Admin Tasks for Repositories
4 -----------------------------------
5
6
7 Manually Force Delete Repository
8 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
9
10 In case of attached forks or pull-requests repositories should be archived.
11 Here is how to force delete a repository and remove all dependent objects
12
13
14 .. code-block:: bash
15
16 # starts the ishell interactive prompt
17 $ rccontrol ishell enterprise-1
18
19 .. code-block:: python
20
21 In [4]: from rhodecode.model.repo import RepoModel
22 In [3]: repo = Repository.get_by_repo_name('test_repos/repo_with_prs')
23 In [5]: RepoModel().delete(repo, forks='detach', pull_requests='delete')
24 In [6]: Session().commit()
@@ -0,0 +1,24 b''
1 .. _user-admin-tasks:
2
3 Common Admin Tasks for Users
4 ----------------------------
5
6
7 Manually Set Personal Repository Group
8 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
9
10 Here is how to set a repository group as personal for a user using ishell.
11
12
13 .. code-block:: bash
14
15 # starts the ishell interactive prompt
16 $ rccontrol ishell enterprise-1
17
18 .. code-block:: python
19
20 In [1]: repo_group = RepoGroup.get_by_group_name('some_group_name')
21 In [2]: user = User.get_by_username('some_user')
22 In [3]: repo_group.user = user
23 In [4]: repo_group.personal = True
24 In [5]: Session().add(repo_group);Session().commit()
@@ -0,0 +1,35 b''
1 .. _search-methods-ref:
2
3 search methods
4 ==============
5
6 search
7 ------
8
9 .. py:function:: search(apiuser, search_query, search_type, page_limit=<Optional:10>, page=<Optional:1>, search_sort=<Optional:'newfirst'>, repo_name=<Optional:None>, repo_group_name=<Optional:None>)
10
11 Fetch Full Text Search results using API.
12
13 :param apiuser: This is filled automatically from the |authtoken|.
14 :type apiuser: AuthUser
15 :param search_query: Search query.
16 :type search_query: str
17 :param search_type: Search type. The following are valid options:
18 * commit
19 * content
20 * path
21 :type search_type: str
22 :param page_limit: Page item limit, from 1 to 500. Default 10 items.
23 :type page_limit: Optional(int)
24 :param page: Page number. Default first page.
25 :type page: Optional(int)
26 :param search_sort: Search sort order. Default newfirst. The following are valid options:
27 * newfirst
28 * oldfirst
29 :type search_sort: Optional(str)
30 :param repo_name: Filter by one repo. Default is all.
31 :type repo_name: Optional(str)
32 :param repo_group_name: Filter by one repo group. Default is all.
33 :type repo_group_name: Optional(str)
34
35
@@ -0,0 +1,85 b''
1 |RCE| 4.17.0 |RNS|
2 ------------------
3
4 Release Date
5 ^^^^^^^^^^^^
6
7 - 2019-07-04
8
9
10 New Features
11 ^^^^^^^^^^^^
12
13 - New artifacts feature.
14 Ability to store binary artifacts for repository with ACL
15 - UI/UX refresh for most of the pages. This includes multiple fixes and improvements.
16 - Diffs: store wide-diff mode in user sessions to store user preference for diff display.
17 - Mercurial: added support for Mercurial 4.9
18 - API: Added search API methods
19 - Files: adding/editing allows previews for generated content.
20 - Files: allowed multi file upload using UI.
21 - Repository Groups: last change is now smartly calculated based on latest change
22 from all it's children repositories.
23 - Archives: it's now currently possible to download partial directories from files view.
24 - SVN: allowed executing pre-commit code with rcextensions, also added example to
25 validate SVN file size and paths on pre-commit level.
26
27
28 General
29 ^^^^^^^
30 - Exception store: add filter for display and deletion.
31 - Files: loading history doesn't display hidden and obsolete commits anymore.
32 - Repositories: bring back missing watch action in summary view.
33 - Admin: user groups is now using pure DB filtering to speed up display
34 for large number of groups.
35 - Mercurial: enabled full evolve+topic extensions when evolve is enabled.
36 - Dependencies: bumped evolve to 8.5.1
37 - Dependencies: bumped pyramid to 1.10.4
38 - Dependencies: bumped psutil to 5.5.1
39 - Dependencies: bumped pygments to 2.4.2
40 - Dependencies: bumped pyramid to 1.10.4
41 - Dependencies: bumped psycopg2 to 2.8.3
42 - Dependencies [security]: updated colander to 1.7.0
43
44
45 Security
46 ^^^^^^^^
47
48 - SSH: replaced pycrypto with cryptography to generate SSH keys as pycrypto isn't
49 considered safe anymore.
50
51
52 Performance
53 ^^^^^^^^^^^
54
55 - Config: updated header limits on gunicorn to prevent errors on large Mercurial repositories.
56 - User sessions: added option to cleanup redis based sessions in user session interface.
57 - Authentication: reduced usage of raw auth calls inside templates to speed up rendering.
58 - Sessions: don't touch session for API calls. Before each API call created new session
59 object which wasn't required.
60
61
62 Fixes
63 ^^^^^
64
65 - hHooks: fixed more unicode problems with new pull-request link generator.
66 - Mercurial: fix ssh-server support for mercurial custom options.
67 - Pull requests: updated metadata information for failed merges with multiple heads.
68 - Pull requests: calculate ancestor in the same way as creation mode.
69 Fixed problem with updates generating wrong diffs in case of merges.
70 - Pull requests: fixed a bug in removal of multiple reviewers at once.
71 - Summary: fix timeout issues loading summary page without styling.
72 - SSH: fix invocation of custom hgrc.
73 - SSH: call custom hooks via SSH backend
74 - Markup: fix styling for check-lists.
75 - Archives: allows downloading refs that have slashes and special refs. e.g f/feat1 branch names.
76 - Files: ensure we generate archives with consistent hashing (except for .tar.gz which uses temp files names in header)
77 - Files: fixed rendering of readme files under non-ascii paths.
78
79
80 Upgrade notes
81 ^^^^^^^^^^^^^
82
83 - In this release we introduced new UI across the application.
84 In case of problems with the display on your systems please send us info to support@rhodecode.com.
85
@@ -0,0 +1,19 b''
1 # contains not directly required libraries we want to pin the version.
2
3 atomicwrites==1.2.1
4 attrs==18.2.0
5 billiard==3.5.0.3
6 chameleon==2.24
7 cffi==1.12.2
8 ecdsa==0.13.2
9 hupper==1.6.1
10 gnureadline==6.3.8
11 jinja2==2.9.6
12 jsonschema==2.6.0
13 pyramid-jinja2==2.7
14 pluggy==0.11.0
15 setproctitle==1.1.10
16 scandir==1.10.0
17 tempita==0.5.2
18 vine==1.3.0
19 configparser==3.7.4
@@ -0,0 +1,93 b''
1 # -*- coding: utf-8 -*-
2
3 # Copyright (C) 2010-2019 RhodeCode GmbH
4 #
5 # This program is free software: you can redistribute it and/or modify
6 # it under the terms of the GNU Affero General Public License, version 3
7 # (only), as published by the Free Software Foundation.
8 #
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # GNU General Public License for more details.
13 #
14 # You should have received a copy of the GNU Affero General Public License
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16 #
17 # This program is dual-licensed. If you wish to learn more about the
18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20
21 import pytest
22 from rhodecode.tests import HG_REPO
23 from rhodecode.api.tests.utils import (
24 build_data, api_call, assert_error, assert_ok)
25
26
27 @pytest.mark.usefixtures("testuser_api", "app")
28 class TestApiSearch(object):
29
30 @pytest.mark.parametrize("query, expected_hits, expected_paths", [
31 ('todo', 23, [
32 'vcs/backends/hg/inmemory.py',
33 'vcs/tests/test_git.py']),
34 ('extension:rst installation', 6, [
35 'docs/index.rst',
36 'docs/installation.rst']),
37 ('def repo', 87, [
38 'vcs/tests/test_git.py',
39 'vcs/tests/test_changesets.py']),
40 ('repository:%s def test' % HG_REPO, 18, [
41 'vcs/tests/test_git.py',
42 'vcs/tests/test_changesets.py']),
43 ('"def main"', 9, [
44 'vcs/__init__.py',
45 'vcs/tests/__init__.py',
46 'vcs/utils/progressbar.py']),
47 ('owner:test_admin', 358, [
48 'vcs/tests/base.py',
49 'MANIFEST.in',
50 'vcs/utils/termcolors.py',
51 'docs/theme/ADC/static/documentation.png']),
52 ('owner:test_admin def main', 72, [
53 'vcs/__init__.py',
54 'vcs/tests/test_utils_filesize.py',
55 'vcs/tests/test_cli.py']),
56 ('owner:michał test', 0, []),
57 ])
58 def test_search_content_results(self, query, expected_hits, expected_paths):
59 id_, params = build_data(
60 self.apikey_regular, 'search',
61 search_query=query,
62 search_type='content')
63
64 response = api_call(self.app, params)
65 json_response = response.json
66
67 assert json_response['result']['item_count'] == expected_hits
68 paths = [x['f_path'] for x in json_response['result']['results']]
69
70 for expected_path in expected_paths:
71 assert expected_path in paths
72
73 @pytest.mark.parametrize("query, expected_hits, expected_paths", [
74 ('readme.rst', 3, []),
75 ('test*', 75, []),
76 ('*model*', 1, []),
77 ('extension:rst', 48, []),
78 ('extension:rst api', 24, []),
79 ])
80 def test_search_file_paths(self, query, expected_hits, expected_paths):
81 id_, params = build_data(
82 self.apikey_regular, 'search',
83 search_query=query,
84 search_type='path')
85
86 response = api_call(self.app, params)
87 json_response = response.json
88
89 assert json_response['result']['item_count'] == expected_hits
90 paths = [x['f_path'] for x in json_response['result']['results']]
91
92 for expected_path in expected_paths:
93 assert expected_path in paths
@@ -0,0 +1,112 b''
1 # -*- coding: utf-8 -*-
2
3 # Copyright (C) 2011-2019 RhodeCode GmbH
4 #
5 # This program is free software: you can redistribute it and/or modify
6 # it under the terms of the GNU Affero General Public License, version 3
7 # (only), as published by the Free Software Foundation.
8 #
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # GNU General Public License for more details.
13 #
14 # You should have received a copy of the GNU Affero General Public License
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16 #
17 # This program is dual-licensed. If you wish to learn more about the
18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20
21
22 import logging
23
24 from rhodecode.api import jsonrpc_method
25 from rhodecode.api.exc import JSONRPCValidationError
26 from rhodecode.api.utils import Optional
27 from rhodecode.lib.index import searcher_from_config
28 from rhodecode.model import validation_schema
29 from rhodecode.model.validation_schema.schemas import search_schema
30
31 log = logging.getLogger(__name__)
32
33
34 @jsonrpc_method()
35 def search(request, apiuser, search_query, search_type, page_limit=Optional(10),
36 page=Optional(1), search_sort=Optional('newfirst'),
37 repo_name=Optional(None), repo_group_name=Optional(None)):
38 """
39 Fetch Full Text Search results using API.
40
41 :param apiuser: This is filled automatically from the |authtoken|.
42 :type apiuser: AuthUser
43 :param search_query: Search query.
44 :type search_query: str
45 :param search_type: Search type. The following are valid options:
46 * commit
47 * content
48 * path
49 :type search_type: str
50 :param page_limit: Page item limit, from 1 to 500. Default 10 items.
51 :type page_limit: Optional(int)
52 :param page: Page number. Default first page.
53 :type page: Optional(int)
54 :param search_sort: Search sort order. Default newfirst. The following are valid options:
55 * newfirst
56 * oldfirst
57 :type search_sort: Optional(str)
58 :param repo_name: Filter by one repo. Default is all.
59 :type repo_name: Optional(str)
60 :param repo_group_name: Filter by one repo group. Default is all.
61 :type repo_group_name: Optional(str)
62 """
63
64 data = {'execution_time': ''}
65 repo_name = Optional.extract(repo_name)
66 repo_group_name = Optional.extract(repo_group_name)
67
68 schema = search_schema.SearchParamsSchema()
69
70 try:
71 search_params = schema.deserialize(
72 dict(search_query=search_query,
73 search_type=search_type,
74 search_sort=Optional.extract(search_sort),
75 page_limit=Optional.extract(page_limit),
76 requested_page=Optional.extract(page))
77 )
78 except validation_schema.Invalid as err:
79 raise JSONRPCValidationError(colander_exc=err)
80
81 search_query = search_params.get('search_query')
82 search_type = search_params.get('search_type')
83 search_sort = search_params.get('search_sort')
84
85 if search_params.get('search_query'):
86 page_limit = search_params['page_limit']
87 requested_page = search_params['requested_page']
88
89 searcher = searcher_from_config(request.registry.settings)
90
91 try:
92 search_result = searcher.search(
93 search_query, search_type, apiuser, repo_name, repo_group_name,
94 requested_page=requested_page, page_limit=page_limit, sort=search_sort)
95
96 data.update(dict(
97 results=list(search_result['results']), page=requested_page,
98 item_count=search_result['count'],
99 items_per_page=page_limit))
100 finally:
101 searcher.cleanup()
102
103 if not search_result['error']:
104 data['execution_time'] = '%s results (%.3f seconds)' % (
105 search_result['count'],
106 search_result['runtime'])
107 else:
108 node = schema['search_query']
109 raise JSONRPCValidationError(
110 colander_exc=validation_schema.Invalid(node, search_result['error']))
111
112 return data
@@ -0,0 +1,48 b''
1 # -*- coding: utf-8 -*-
2
3 # Copyright (C) 2011-2019 RhodeCode GmbH
4 #
5 # This program is free software: you can redistribute it and/or modify
6 # it under the terms of the GNU Affero General Public License, version 3
7 # (only), as published by the Free Software Foundation.
8 #
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # GNU General Public License for more details.
13 #
14 # You should have received a copy of the GNU Affero General Public License
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16 #
17 # This program is dual-licensed. If you wish to learn more about the
18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20
21 import logging
22
23 from pyramid.view import view_config
24
25 from rhodecode.apps._base import RepoAppView
26 from rhodecode.lib.auth import (
27 LoginRequired, HasRepoPermissionAnyDecorator)
28
29 log = logging.getLogger(__name__)
30
31
32 class RepoArtifactsView(RepoAppView):
33
34 def load_default_context(self):
35 c = self._get_local_tmpl_context(include_app_defaults=True)
36 c.rhodecode_repo = self.rhodecode_vcs_repo
37 return c
38
39 @LoginRequired()
40 @HasRepoPermissionAnyDecorator(
41 'repository.read', 'repository.write', 'repository.admin')
42 @view_config(
43 route_name='repo_artifacts_list', request_method='GET',
44 renderer='rhodecode:templates/artifacts/artifact_list.mako')
45 def repo_artifacts(self):
46 c = self.load_default_context()
47 c.active = 'artifacts'
48 return self._get_template_context(c)
@@ -0,0 +1,55 b''
1 # -*- coding: utf-8 -*-
2
3 import logging
4
5 from alembic.migration import MigrationContext
6 from alembic.operations import Operations
7 from sqlalchemy import String, Column
8 from sqlalchemy.sql import text
9
10 from rhodecode.lib.dbmigrate.versions import _reset_base
11 from rhodecode.lib.utils2 import safe_str
12 from rhodecode.model import meta, init_model_encryption
13 from rhodecode.model.db import RepoGroup
14
15
16 log = logging.getLogger(__name__)
17
18
19 def upgrade(migrate_engine):
20 """
21 Upgrade operations go here.
22 Don't create your own engine; bind migrate_engine to your metadata
23 """
24 _reset_base(migrate_engine)
25 from rhodecode.lib.dbmigrate.schema import db_4_16_0_2
26
27 init_model_encryption(db_4_16_0_2)
28
29 context = MigrationContext.configure(migrate_engine.connect())
30 op = Operations(context)
31
32 repo_group = db_4_16_0_2.RepoGroup.__table__
33
34 with op.batch_alter_table(repo_group.name) as batch_op:
35 batch_op.add_column(
36 Column("repo_group_name_hash", String(1024), nullable=True, unique=False))
37
38 _generate_repo_group_name_hashes(db_4_16_0_2, op, meta.Session)
39
40
41 def downgrade(migrate_engine):
42 pass
43
44
45 def _generate_repo_group_name_hashes(models, op, session):
46 repo_groups = models.RepoGroup.get_all()
47 for repo_group in repo_groups:
48 print(safe_str(repo_group.group_name))
49 hash_ = RepoGroup.hash_repo_group_name(repo_group.group_name)
50 params = {'hash': hash_, 'id': repo_group.group_id}
51 query = text(
52 'UPDATE groups SET repo_group_name_hash = :hash'
53 ' WHERE group_id = :id').bindparams(**params)
54 op.execute(query)
55 session().commit()
@@ -0,0 +1,35 b''
1 # -*- coding: utf-8 -*-
2
3 import logging
4
5 from alembic.migration import MigrationContext
6 from alembic.operations import Operations
7
8 from rhodecode.lib.dbmigrate.versions import _reset_base
9 from rhodecode.model import init_model_encryption
10
11
12 log = logging.getLogger(__name__)
13
14
15 def upgrade(migrate_engine):
16 """
17 Upgrade operations go here.
18 Don't create your own engine; bind migrate_engine to your metadata
19 """
20 _reset_base(migrate_engine)
21 from rhodecode.lib.dbmigrate.schema import db_4_16_0_2
22
23 init_model_encryption(db_4_16_0_2)
24
25 context = MigrationContext.configure(migrate_engine.connect())
26 op = Operations(context)
27
28 repo_group = db_4_16_0_2.RepoGroup.__table__
29
30 with op.batch_alter_table(repo_group.name) as batch_op:
31 batch_op.alter_column("repo_group_name_hash", nullable=False)
32
33
34 def downgrade(migrate_engine):
35 pass
@@ -0,0 +1,37 b''
1 # -*- coding: utf-8 -*-
2
3 import logging
4
5 from alembic.migration import MigrationContext
6 from alembic.operations import Operations
7 from sqlalchemy import Column, LargeBinary
8
9 from rhodecode.lib.dbmigrate.versions import _reset_base
10 from rhodecode.model import init_model_encryption
11
12
13 log = logging.getLogger(__name__)
14
15
16 def upgrade(migrate_engine):
17 """
18 Upgrade operations go here.
19 Don't create your own engine; bind migrate_engine to your metadata
20 """
21 _reset_base(migrate_engine)
22 from rhodecode.lib.dbmigrate.schema import db_4_16_0_2
23
24 init_model_encryption(db_4_16_0_2)
25
26 context = MigrationContext.configure(migrate_engine.connect())
27 op = Operations(context)
28
29 repo_group = db_4_16_0_2.RepoGroup.__table__
30
31 with op.batch_alter_table(repo_group.name) as batch_op:
32 batch_op.add_column(
33 Column("changeset_cache", LargeBinary(1024), nullable=True))
34
35
36 def downgrade(migrate_engine):
37 pass
@@ -0,0 +1,69 b''
1 import os
2 import base64
3 from cryptography.fernet import Fernet, InvalidToken
4 from cryptography.hazmat.backends import default_backend
5 from cryptography.hazmat.primitives import hashes
6 from cryptography.hazmat.primitives.kdf.pbkdf2 import PBKDF2HMAC
7
8
9 class Encryptor(object):
10 key_format = 'enc2$salt:{}$data:{}'
11 pref_len = 5 # salt:, data:
12
13 def __init__(self, enc_key):
14 self.enc_key = enc_key
15
16 def b64_encode(self, data):
17 return base64.urlsafe_b64encode(data)
18
19 def b64_decode(self, data):
20 return base64.urlsafe_b64decode(data)
21
22 def get_encryptor(self, salt):
23 """
24 Uses Fernet as encryptor with HMAC signature
25 :param salt: random salt used for encrypting the data
26 """
27 kdf = PBKDF2HMAC(
28 algorithm=hashes.SHA512(),
29 length=32,
30 salt=salt,
31 iterations=100000,
32 backend=default_backend()
33 )
34 key = self.b64_encode(kdf.derive(self.enc_key))
35 return Fernet(key)
36
37 def _get_parts(self, enc_data):
38 parts = enc_data.split('$', 3)
39 if len(parts) != 3:
40 raise ValueError('Encrypted Data has invalid format, expected {}'.format(self.key_format))
41 prefix, salt, enc_data = parts
42
43 try:
44 salt = self.b64_decode(salt[self.pref_len:])
45 except TypeError:
46 # bad base64
47 raise ValueError('Encrypted Data salt invalid format, expected base64 format')
48
49 enc_data = enc_data[self.pref_len:]
50 return prefix, salt, enc_data
51
52 def encrypt(self, data):
53 salt = os.urandom(64)
54 encryptor = self.get_encryptor(salt)
55 enc_data = encryptor.encrypt(data)
56 return self.key_format.format(self.b64_encode(salt), enc_data)
57
58 def decrypt(self, data, safe=True):
59 parts = self._get_parts(data)
60 salt = parts[1]
61 enc_data = parts[2]
62 encryptor = self.get_encryptor(salt)
63 try:
64 return encryptor.decrypt(enc_data)
65 except (InvalidToken,):
66 if safe:
67 return ''
68 else:
69 raise
@@ -0,0 +1,200 b''
1 # Copyright (c) 2010 Agendaless Consulting and Contributors.
2 # (http://www.agendaless.com), All Rights Reserved
3 # License: BSD-derived (http://www.repoze.org/LICENSE.txt)
4 # With Patches from RhodeCode GmBH
5
6
7 import os
8
9 from beaker import cache
10 from beaker.session import SessionObject
11 from beaker.util import coerce_cache_params
12 from beaker.util import coerce_session_params
13
14 from pyramid.interfaces import ISession
15 from pyramid.settings import asbool
16 from zope.interface import implementer
17
18 from binascii import hexlify
19
20
21 def BeakerSessionFactoryConfig(**options):
22 """ Return a Pyramid session factory using Beaker session settings
23 supplied directly as ``**options``"""
24
25 class PyramidBeakerSessionObject(SessionObject):
26 _options = options
27 _cookie_on_exception = _options.pop('cookie_on_exception', True)
28 _constant_csrf_token = _options.pop('constant_csrf_token', False)
29
30 def __init__(self, request):
31 SessionObject.__init__(self, request.environ, **self._options)
32
33 def session_callback(request, response):
34 exception = getattr(request, 'exception', None)
35 if (exception is None or self._cookie_on_exception) and self.accessed():
36 self.persist()
37 headers = self.__dict__['_headers']
38 if headers['set_cookie'] and headers['cookie_out']:
39 response.headerlist.append(('Set-Cookie', headers['cookie_out']))
40 request.add_response_callback(session_callback)
41
42 # ISession API
43
44 @property
45 def id(self):
46 # this is as inspected in SessionObject.__init__
47 if self.__dict__['_params'].get('type') != 'cookie':
48 return self._session().id
49 return None
50
51 @property
52 def new(self):
53 return self.last_accessed is None
54
55 changed = SessionObject.save
56
57 # modifying dictionary methods
58
59 @call_save
60 def clear(self):
61 return self._session().clear()
62
63 @call_save
64 def update(self, d, **kw):
65 return self._session().update(d, **kw)
66
67 @call_save
68 def setdefault(self, k, d=None):
69 return self._session().setdefault(k, d)
70
71 @call_save
72 def pop(self, k, d=None):
73 return self._session().pop(k, d)
74
75 @call_save
76 def popitem(self):
77 return self._session().popitem()
78
79 __setitem__ = call_save(SessionObject.__setitem__)
80 __delitem__ = call_save(SessionObject.__delitem__)
81
82 # Flash API methods
83 def flash(self, msg, queue='', allow_duplicate=True):
84 storage = self.setdefault('_f_' + queue, [])
85 if allow_duplicate or (msg not in storage):
86 storage.append(msg)
87
88 def pop_flash(self, queue=''):
89 storage = self.pop('_f_' + queue, [])
90 return storage
91
92 def peek_flash(self, queue=''):
93 storage = self.get('_f_' + queue, [])
94 return storage
95
96 # CSRF API methods
97 def new_csrf_token(self):
98 token = (self._constant_csrf_token
99 or hexlify(os.urandom(20)).decode('ascii'))
100 self['_csrft_'] = token
101 return token
102
103 def get_csrf_token(self):
104 token = self.get('_csrft_', None)
105 if token is None:
106 token = self.new_csrf_token()
107 return token
108
109 return implementer(ISession)(PyramidBeakerSessionObject)
110
111
112 def call_save(wrapped):
113 """ By default, in non-auto-mode beaker badly wants people to
114 call save even though it should know something has changed when
115 a mutating method is called. This hack should be removed if
116 Beaker ever starts to do this by default. """
117 def save(session, *arg, **kw):
118 value = wrapped(session, *arg, **kw)
119 session.save()
120 return value
121 save.__doc__ = wrapped.__doc__
122 return save
123
124
125 def session_factory_from_settings(settings):
126 """ Return a Pyramid session factory using Beaker session settings
127 supplied from a Paste configuration file"""
128 prefixes = ('session.', 'beaker.session.')
129 options = {}
130
131 # Pull out any config args meant for beaker session. if there are any
132 for k, v in settings.items():
133 for prefix in prefixes:
134 if k.startswith(prefix):
135 option_name = k[len(prefix):]
136 if option_name == 'cookie_on_exception':
137 v = asbool(v)
138 options[option_name] = v
139
140 options = coerce_session_params(options)
141 return BeakerSessionFactoryConfig(**options)
142
143
144 def set_cache_regions_from_settings(settings):
145 """ Add cache support to the Pylons application.
146
147 The ``settings`` passed to the configurator are used to setup
148 the cache options. Cache options in the settings should start
149 with either 'beaker.cache.' or 'cache.'.
150
151 """
152 cache_settings = {'regions': []}
153 for key in settings.keys():
154 for prefix in ['beaker.cache.', 'cache.']:
155 if key.startswith(prefix):
156 name = key.split(prefix)[1].strip()
157 cache_settings[name] = settings[key].strip()
158
159 if ('expire' in cache_settings
160 and isinstance(cache_settings['expire'], basestring)
161 and cache_settings['expire'].lower() in ['none', 'no']):
162 cache_settings['expire'] = None
163
164 coerce_cache_params(cache_settings)
165
166 if 'enabled' not in cache_settings:
167 cache_settings['enabled'] = True
168
169 regions = cache_settings['regions']
170 if regions:
171 for region in regions:
172 if not region:
173 continue
174
175 region_settings = {
176 'data_dir': cache_settings.get('data_dir'),
177 'lock_dir': cache_settings.get('lock_dir'),
178 'expire': cache_settings.get('expire', 60),
179 'enabled': cache_settings['enabled'],
180 'key_length': cache_settings.get('key_length', 250),
181 'type': cache_settings.get('type'),
182 'url': cache_settings.get('url'),
183 }
184 region_prefix = '%s.' % region
185 region_len = len(region_prefix)
186 for key in list(cache_settings.keys()):
187 if key.startswith(region_prefix):
188 region_settings[key[region_len:]] = cache_settings.pop(key)
189
190 if (isinstance(region_settings['expire'], basestring)
191 and region_settings['expire'].lower() in ['none', 'no']):
192 region_settings['expire'] = None
193 coerce_cache_params(region_settings)
194 cache.cache_regions[region] = region_settings
195
196
197 def includeme(config):
198 session_factory = session_factory_from_settings(config.registry.settings)
199 config.set_session_factory(session_factory)
200 set_cache_regions_from_settings(config.registry.settings)
This diff has been collapsed as it changes many lines, (11669 lines changed) Show them Hide them
@@ -0,0 +1,11669 b''
1 div.ipynb {
2 /*!
3 *
4 * Twitter Bootstrap
5 *
6 */
7 /*!
8 * Bootstrap v3.3.7 (http://getbootstrap.com)
9 * Copyright 2011-2016 Twitter, Inc.
10 * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
11 */
12 /*! normalize.css v3.0.3 | MIT License | github.com/necolas/normalize.css */
13 html {
14 font-family: sans-serif;
15 -ms-text-size-adjust: 100%;
16 -webkit-text-size-adjust: 100%;
17 }
18 body {
19 margin: 0;
20 }
21 article,
22 aside,
23 details,
24 figcaption,
25 figure,
26 footer,
27 header,
28 hgroup,
29 main,
30 menu,
31 nav,
32 section,
33 summary {
34 display: block;
35 }
36 audio,
37 canvas,
38 progress,
39 video {
40 display: inline-block;
41 vertical-align: baseline;
42 }
43 audio:not([controls]) {
44 display: none;
45 height: 0;
46 }
47 [hidden],
48 template {
49 display: none;
50 }
51 a {
52 background-color: transparent;
53 }
54 a:active,
55 a:hover {
56 outline: 0;
57 }
58 abbr[title] {
59 border-bottom: 1px dotted;
60 }
61 b,
62 strong {
63 font-weight: bold;
64 }
65 dfn {
66 font-style: italic;
67 }
68 h1 {
69 font-size: 2em;
70 margin: 0.67em 0;
71 }
72 mark {
73 background: #ff0;
74 color: #000;
75 }
76 small {
77 font-size: 80%;
78 }
79 sub,
80 sup {
81 font-size: 75%;
82 line-height: 0;
83 position: relative;
84 vertical-align: baseline;
85 }
86 sup {
87 top: -0.5em;
88 }
89 sub {
90 bottom: -0.25em;
91 }
92 img {
93 border: 0;
94 }
95 svg:not(:root) {
96 overflow: hidden;
97 }
98 figure {
99 margin: 1em 40px;
100 }
101 hr {
102 box-sizing: content-box;
103 height: 0;
104 }
105 pre {
106 overflow: auto;
107 }
108 code,
109 kbd,
110 pre,
111 samp {
112 font-family: monospace, monospace;
113 font-size: 1em;
114 }
115 button,
116 input,
117 optgroup,
118 select,
119 textarea {
120 color: inherit;
121 font: inherit;
122 margin: 0;
123 }
124 button {
125 overflow: visible;
126 }
127 button,
128 select {
129 text-transform: none;
130 }
131 button,
132 html input[type="button"],
133 input[type="reset"],
134 input[type="submit"] {
135 -webkit-appearance: button;
136 cursor: pointer;
137 }
138 button[disabled],
139 html input[disabled] {
140 cursor: default;
141 }
142 button::-moz-focus-inner,
143 input::-moz-focus-inner {
144 border: 0;
145 padding: 0;
146 }
147 input {
148 line-height: normal;
149 }
150 input[type="checkbox"],
151 input[type="radio"] {
152 box-sizing: border-box;
153 padding: 0;
154 }
155 input[type="number"]::-webkit-inner-spin-button,
156 input[type="number"]::-webkit-outer-spin-button {
157 height: auto;
158 }
159 input[type="search"] {
160 -webkit-appearance: textfield;
161 box-sizing: content-box;
162 }
163 input[type="search"]::-webkit-search-cancel-button,
164 input[type="search"]::-webkit-search-decoration {
165 -webkit-appearance: none;
166 }
167 fieldset {
168 border: 1px solid #c0c0c0;
169 margin: 0 2px;
170 padding: 0.35em 0.625em 0.75em;
171 }
172 legend {
173 border: 0;
174 padding: 0;
175 }
176 textarea {
177 overflow: auto;
178 }
179 optgroup {
180 font-weight: bold;
181 }
182 table {
183 border-collapse: collapse;
184 border-spacing: 0;
185 }
186 td,
187 th {
188 padding: 0;
189 }
190 /*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */
191 @media print {
192 *,
193 *:before,
194 *:after {
195 background: transparent !important;
196 color: #000 !important;
197 box-shadow: none !important;
198 text-shadow: none !important;
199 }
200 a,
201 a:visited {
202 text-decoration: underline;
203 }
204 a[href]:after {
205 content: " (" attr(href) ")";
206 }
207 abbr[title]:after {
208 content: " (" attr(title) ")";
209 }
210 a[href^="#"]:after,
211 a[href^="javascript:"]:after {
212 content: "";
213 }
214 pre,
215 blockquote {
216 border: 1px solid #999;
217 page-break-inside: avoid;
218 }
219 thead {
220 display: table-header-group;
221 }
222 tr,
223 img {
224 page-break-inside: avoid;
225 }
226 img {
227 max-width: 100% !important;
228 }
229 p,
230 h2,
231 h3 {
232 orphans: 3;
233 widows: 3;
234 }
235 h2,
236 h3 {
237 page-break-after: avoid;
238 }
239 .navbar {
240 display: none;
241 }
242 .btn > .caret,
243 .dropup > .btn > .caret {
244 border-top-color: #000 !important;
245 }
246 .label {
247 border: 1px solid #000;
248 }
249 .table {
250 border-collapse: collapse !important;
251 }
252 .table td,
253 .table th {
254 background-color: #fff !important;
255 }
256 .table-bordered th,
257 .table-bordered td {
258 border: 1px solid #ddd !important;
259 }
260 }
261 @font-face {
262 font-family: 'Glyphicons Halflings';
263 src: url('../components/bootstrap/fonts/glyphicons-halflings-regular.eot');
264 src: url('../components/bootstrap/fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'), url('../components/bootstrap/fonts/glyphicons-halflings-regular.woff2') format('woff2'), url('../components/bootstrap/fonts/glyphicons-halflings-regular.woff') format('woff'), url('../components/bootstrap/fonts/glyphicons-halflings-regular.ttf') format('truetype'), url('../components/bootstrap/fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg');
265 }
266 .glyphicon {
267 position: relative;
268 top: 1px;
269 display: inline-block;
270 font-family: 'Glyphicons Halflings';
271 font-style: normal;
272 font-weight: normal;
273 line-height: 1;
274 -webkit-font-smoothing: antialiased;
275 -moz-osx-font-smoothing: grayscale;
276 }
277 .glyphicon-asterisk:before {
278 content: "\002a";
279 }
280 .glyphicon-plus:before {
281 content: "\002b";
282 }
283 .glyphicon-euro:before,
284 .glyphicon-eur:before {
285 content: "\20ac";
286 }
287 .glyphicon-minus:before {
288 content: "\2212";
289 }
290 .glyphicon-cloud:before {
291 content: "\2601";
292 }
293 .glyphicon-envelope:before {
294 content: "\2709";
295 }
296 .glyphicon-pencil:before {
297 content: "\270f";
298 }
299 .glyphicon-glass:before {
300 content: "\e001";
301 }
302 .glyphicon-music:before {
303 content: "\e002";
304 }
305 .glyphicon-search:before {
306 content: "\e003";
307 }
308 .glyphicon-heart:before {
309 content: "\e005";
310 }
311 .glyphicon-star:before {
312 content: "\e006";
313 }
314 .glyphicon-star-empty:before {
315 content: "\e007";
316 }
317 .glyphicon-user:before {
318 content: "\e008";
319 }
320 .glyphicon-film:before {
321 content: "\e009";
322 }
323 .glyphicon-th-large:before {
324 content: "\e010";
325 }
326 .glyphicon-th:before {
327 content: "\e011";
328 }
329 .glyphicon-th-list:before {
330 content: "\e012";
331 }
332 .glyphicon-ok:before {
333 content: "\e013";
334 }
335 .glyphicon-remove:before {
336 content: "\e014";
337 }
338 .glyphicon-zoom-in:before {
339 content: "\e015";
340 }
341 .glyphicon-zoom-out:before {
342 content: "\e016";
343 }
344 .glyphicon-off:before {
345 content: "\e017";
346 }
347 .glyphicon-signal:before {
348 content: "\e018";
349 }
350 .glyphicon-cog:before {
351 content: "\e019";
352 }
353 .glyphicon-trash:before {
354 content: "\e020";
355 }
356 .glyphicon-home:before {
357 content: "\e021";
358 }
359 .glyphicon-file:before {
360 content: "\e022";
361 }
362 .glyphicon-time:before {
363 content: "\e023";
364 }
365 .glyphicon-road:before {
366 content: "\e024";
367 }
368 .glyphicon-download-alt:before {
369 content: "\e025";
370 }
371 .glyphicon-download:before {
372 content: "\e026";
373 }
374 .glyphicon-upload:before {
375 content: "\e027";
376 }
377 .glyphicon-inbox:before {
378 content: "\e028";
379 }
380 .glyphicon-play-circle:before {
381 content: "\e029";
382 }
383 .glyphicon-repeat:before {
384 content: "\e030";
385 }
386 .glyphicon-refresh:before {
387 content: "\e031";
388 }
389 .glyphicon-list-alt:before {
390 content: "\e032";
391 }
392 .glyphicon-lock:before {
393 content: "\e033";
394 }
395 .glyphicon-flag:before {
396 content: "\e034";
397 }
398 .glyphicon-headphones:before {
399 content: "\e035";
400 }
401 .glyphicon-volume-off:before {
402 content: "\e036";
403 }
404 .glyphicon-volume-down:before {
405 content: "\e037";
406 }
407 .glyphicon-volume-up:before {
408 content: "\e038";
409 }
410 .glyphicon-qrcode:before {
411 content: "\e039";
412 }
413 .glyphicon-barcode:before {
414 content: "\e040";
415 }
416 .glyphicon-tag:before {
417 content: "\e041";
418 }
419 .glyphicon-tags:before {
420 content: "\e042";
421 }
422 .glyphicon-book:before {
423 content: "\e043";
424 }
425 .glyphicon-bookmark:before {
426 content: "\e044";
427 }
428 .glyphicon-print:before {
429 content: "\e045";
430 }
431 .glyphicon-camera:before {
432 content: "\e046";
433 }
434 .glyphicon-font:before {
435 content: "\e047";
436 }
437 .glyphicon-bold:before {
438 content: "\e048";
439 }
440 .glyphicon-italic:before {
441 content: "\e049";
442 }
443 .glyphicon-text-height:before {
444 content: "\e050";
445 }
446 .glyphicon-text-width:before {
447 content: "\e051";
448 }
449 .glyphicon-align-left:before {
450 content: "\e052";
451 }
452 .glyphicon-align-center:before {
453 content: "\e053";
454 }
455 .glyphicon-align-right:before {
456 content: "\e054";
457 }
458 .glyphicon-align-justify:before {
459 content: "\e055";
460 }
461 .glyphicon-list:before {
462 content: "\e056";
463 }
464 .glyphicon-indent-left:before {
465 content: "\e057";
466 }
467 .glyphicon-indent-right:before {
468 content: "\e058";
469 }
470 .glyphicon-facetime-video:before {
471 content: "\e059";
472 }
473 .glyphicon-picture:before {
474 content: "\e060";
475 }
476 .glyphicon-map-marker:before {
477 content: "\e062";
478 }
479 .glyphicon-adjust:before {
480 content: "\e063";
481 }
482 .glyphicon-tint:before {
483 content: "\e064";
484 }
485 .glyphicon-edit:before {
486 content: "\e065";
487 }
488 .glyphicon-share:before {
489 content: "\e066";
490 }
491 .glyphicon-check:before {
492 content: "\e067";
493 }
494 .glyphicon-move:before {
495 content: "\e068";
496 }
497 .glyphicon-step-backward:before {
498 content: "\e069";
499 }
500 .glyphicon-fast-backward:before {
501 content: "\e070";
502 }
503 .glyphicon-backward:before {
504 content: "\e071";
505 }
506 .glyphicon-play:before {
507 content: "\e072";
508 }
509 .glyphicon-pause:before {
510 content: "\e073";
511 }
512 .glyphicon-stop:before {
513 content: "\e074";
514 }
515 .glyphicon-forward:before {
516 content: "\e075";
517 }
518 .glyphicon-fast-forward:before {
519 content: "\e076";
520 }
521 .glyphicon-step-forward:before {
522 content: "\e077";
523 }
524 .glyphicon-eject:before {
525 content: "\e078";
526 }
527 .glyphicon-chevron-left:before {
528 content: "\e079";
529 }
530 .glyphicon-chevron-right:before {
531 content: "\e080";
532 }
533 .glyphicon-plus-sign:before {
534 content: "\e081";
535 }
536 .glyphicon-minus-sign:before {
537 content: "\e082";
538 }
539 .glyphicon-remove-sign:before {
540 content: "\e083";
541 }
542 .glyphicon-ok-sign:before {
543 content: "\e084";
544 }
545 .glyphicon-question-sign:before {
546 content: "\e085";
547 }
548 .glyphicon-info-sign:before {
549 content: "\e086";
550 }
551 .glyphicon-screenshot:before {
552 content: "\e087";
553 }
554 .glyphicon-remove-circle:before {
555 content: "\e088";
556 }
557 .glyphicon-ok-circle:before {
558 content: "\e089";
559 }
560 .glyphicon-ban-circle:before {
561 content: "\e090";
562 }
563 .glyphicon-arrow-left:before {
564 content: "\e091";
565 }
566 .glyphicon-arrow-right:before {
567 content: "\e092";
568 }
569 .glyphicon-arrow-up:before {
570 content: "\e093";
571 }
572 .glyphicon-arrow-down:before {
573 content: "\e094";
574 }
575 .glyphicon-share-alt:before {
576 content: "\e095";
577 }
578 .glyphicon-resize-full:before {
579 content: "\e096";
580 }
581 .glyphicon-resize-small:before {
582 content: "\e097";
583 }
584 .glyphicon-exclamation-sign:before {
585 content: "\e101";
586 }
587 .glyphicon-gift:before {
588 content: "\e102";
589 }
590 .glyphicon-leaf:before {
591 content: "\e103";
592 }
593 .glyphicon-fire:before {
594 content: "\e104";
595 }
596 .glyphicon-eye-open:before {
597 content: "\e105";
598 }
599 .glyphicon-eye-close:before {
600 content: "\e106";
601 }
602 .glyphicon-warning-sign:before {
603 content: "\e107";
604 }
605 .glyphicon-plane:before {
606 content: "\e108";
607 }
608 .glyphicon-calendar:before {
609 content: "\e109";
610 }
611 .glyphicon-random:before {
612 content: "\e110";
613 }
614 .glyphicon-comment:before {
615 content: "\e111";
616 }
617 .glyphicon-magnet:before {
618 content: "\e112";
619 }
620 .glyphicon-chevron-up:before {
621 content: "\e113";
622 }
623 .glyphicon-chevron-down:before {
624 content: "\e114";
625 }
626 .glyphicon-retweet:before {
627 content: "\e115";
628 }
629 .glyphicon-shopping-cart:before {
630 content: "\e116";
631 }
632 .glyphicon-folder-close:before {
633 content: "\e117";
634 }
635 .glyphicon-folder-open:before {
636 content: "\e118";
637 }
638 .glyphicon-resize-vertical:before {
639 content: "\e119";
640 }
641 .glyphicon-resize-horizontal:before {
642 content: "\e120";
643 }
644 .glyphicon-hdd:before {
645 content: "\e121";
646 }
647 .glyphicon-bullhorn:before {
648 content: "\e122";
649 }
650 .glyphicon-bell:before {
651 content: "\e123";
652 }
653 .glyphicon-certificate:before {
654 content: "\e124";
655 }
656 .glyphicon-thumbs-up:before {
657 content: "\e125";
658 }
659 .glyphicon-thumbs-down:before {
660 content: "\e126";
661 }
662 .glyphicon-hand-right:before {
663 content: "\e127";
664 }
665 .glyphicon-hand-left:before {
666 content: "\e128";
667 }
668 .glyphicon-hand-up:before {
669 content: "\e129";
670 }
671 .glyphicon-hand-down:before {
672 content: "\e130";
673 }
674 .glyphicon-circle-arrow-right:before {
675 content: "\e131";
676 }
677 .glyphicon-circle-arrow-left:before {
678 content: "\e132";
679 }
680 .glyphicon-circle-arrow-up:before {
681 content: "\e133";
682 }
683 .glyphicon-circle-arrow-down:before {
684 content: "\e134";
685 }
686 .glyphicon-globe:before {
687 content: "\e135";
688 }
689 .glyphicon-wrench:before {
690 content: "\e136";
691 }
692 .glyphicon-tasks:before {
693 content: "\e137";
694 }
695 .glyphicon-filter:before {
696 content: "\e138";
697 }
698 .glyphicon-briefcase:before {
699 content: "\e139";
700 }
701 .glyphicon-fullscreen:before {
702 content: "\e140";
703 }
704 .glyphicon-dashboard:before {
705 content: "\e141";
706 }
707 .glyphicon-paperclip:before {
708 content: "\e142";
709 }
710 .glyphicon-heart-empty:before {
711 content: "\e143";
712 }
713 .glyphicon-link:before {
714 content: "\e144";
715 }
716 .glyphicon-phone:before {
717 content: "\e145";
718 }
719 .glyphicon-pushpin:before {
720 content: "\e146";
721 }
722 .glyphicon-usd:before {
723 content: "\e148";
724 }
725 .glyphicon-gbp:before {
726 content: "\e149";
727 }
728 .glyphicon-sort:before {
729 content: "\e150";
730 }
731 .glyphicon-sort-by-alphabet:before {
732 content: "\e151";
733 }
734 .glyphicon-sort-by-alphabet-alt:before {
735 content: "\e152";
736 }
737 .glyphicon-sort-by-order:before {
738 content: "\e153";
739 }
740 .glyphicon-sort-by-order-alt:before {
741 content: "\e154";
742 }
743 .glyphicon-sort-by-attributes:before {
744 content: "\e155";
745 }
746 .glyphicon-sort-by-attributes-alt:before {
747 content: "\e156";
748 }
749 .glyphicon-unchecked:before {
750 content: "\e157";
751 }
752 .glyphicon-expand:before {
753 content: "\e158";
754 }
755 .glyphicon-collapse-down:before {
756 content: "\e159";
757 }
758 .glyphicon-collapse-up:before {
759 content: "\e160";
760 }
761 .glyphicon-log-in:before {
762 content: "\e161";
763 }
764 .glyphicon-flash:before {
765 content: "\e162";
766 }
767 .glyphicon-log-out:before {
768 content: "\e163";
769 }
770 .glyphicon-new-window:before {
771 content: "\e164";
772 }
773 .glyphicon-record:before {
774 content: "\e165";
775 }
776 .glyphicon-save:before {
777 content: "\e166";
778 }
779 .glyphicon-open:before {
780 content: "\e167";
781 }
782 .glyphicon-saved:before {
783 content: "\e168";
784 }
785 .glyphicon-import:before {
786 content: "\e169";
787 }
788 .glyphicon-export:before {
789 content: "\e170";
790 }
791 .glyphicon-send:before {
792 content: "\e171";
793 }
794 .glyphicon-floppy-disk:before {
795 content: "\e172";
796 }
797 .glyphicon-floppy-saved:before {
798 content: "\e173";
799 }
800 .glyphicon-floppy-remove:before {
801 content: "\e174";
802 }
803 .glyphicon-floppy-save:before {
804 content: "\e175";
805 }
806 .glyphicon-floppy-open:before {
807 content: "\e176";
808 }
809 .glyphicon-credit-card:before {
810 content: "\e177";
811 }
812 .glyphicon-transfer:before {
813 content: "\e178";
814 }
815 .glyphicon-cutlery:before {
816 content: "\e179";
817 }
818 .glyphicon-header:before {
819 content: "\e180";
820 }
821 .glyphicon-compressed:before {
822 content: "\e181";
823 }
824 .glyphicon-earphone:before {
825 content: "\e182";
826 }
827 .glyphicon-phone-alt:before {
828 content: "\e183";
829 }
830 .glyphicon-tower:before {
831 content: "\e184";
832 }
833 .glyphicon-stats:before {
834 content: "\e185";
835 }
836 .glyphicon-sd-video:before {
837 content: "\e186";
838 }
839 .glyphicon-hd-video:before {
840 content: "\e187";
841 }
842 .glyphicon-subtitles:before {
843 content: "\e188";
844 }
845 .glyphicon-sound-stereo:before {
846 content: "\e189";
847 }
848 .glyphicon-sound-dolby:before {
849 content: "\e190";
850 }
851 .glyphicon-sound-5-1:before {
852 content: "\e191";
853 }
854 .glyphicon-sound-6-1:before {
855 content: "\e192";
856 }
857 .glyphicon-sound-7-1:before {
858 content: "\e193";
859 }
860 .glyphicon-copyright-mark:before {
861 content: "\e194";
862 }
863 .glyphicon-registration-mark:before {
864 content: "\e195";
865 }
866 .glyphicon-cloud-download:before {
867 content: "\e197";
868 }
869 .glyphicon-cloud-upload:before {
870 content: "\e198";
871 }
872 .glyphicon-tree-conifer:before {
873 content: "\e199";
874 }
875 .glyphicon-tree-deciduous:before {
876 content: "\e200";
877 }
878 .glyphicon-cd:before {
879 content: "\e201";
880 }
881 .glyphicon-save-file:before {
882 content: "\e202";
883 }
884 .glyphicon-open-file:before {
885 content: "\e203";
886 }
887 .glyphicon-level-up:before {
888 content: "\e204";
889 }
890 .glyphicon-copy:before {
891 content: "\e205";
892 }
893 .glyphicon-paste:before {
894 content: "\e206";
895 }
896 .glyphicon-alert:before {
897 content: "\e209";
898 }
899 .glyphicon-equalizer:before {
900 content: "\e210";
901 }
902 .glyphicon-king:before {
903 content: "\e211";
904 }
905 .glyphicon-queen:before {
906 content: "\e212";
907 }
908 .glyphicon-pawn:before {
909 content: "\e213";
910 }
911 .glyphicon-bishop:before {
912 content: "\e214";
913 }
914 .glyphicon-knight:before {
915 content: "\e215";
916 }
917 .glyphicon-baby-formula:before {
918 content: "\e216";
919 }
920 .glyphicon-tent:before {
921 content: "\26fa";
922 }
923 .glyphicon-blackboard:before {
924 content: "\e218";
925 }
926 .glyphicon-bed:before {
927 content: "\e219";
928 }
929 .glyphicon-apple:before {
930 content: "\f8ff";
931 }
932 .glyphicon-erase:before {
933 content: "\e221";
934 }
935 .glyphicon-hourglass:before {
936 content: "\231b";
937 }
938 .glyphicon-lamp:before {
939 content: "\e223";
940 }
941 .glyphicon-duplicate:before {
942 content: "\e224";
943 }
944 .glyphicon-piggy-bank:before {
945 content: "\e225";
946 }
947 .glyphicon-scissors:before {
948 content: "\e226";
949 }
950 .glyphicon-bitcoin:before {
951 content: "\e227";
952 }
953 .glyphicon-btc:before {
954 content: "\e227";
955 }
956 .glyphicon-xbt:before {
957 content: "\e227";
958 }
959 .glyphicon-yen:before {
960 content: "\00a5";
961 }
962 .glyphicon-jpy:before {
963 content: "\00a5";
964 }
965 .glyphicon-ruble:before {
966 content: "\20bd";
967 }
968 .glyphicon-rub:before {
969 content: "\20bd";
970 }
971 .glyphicon-scale:before {
972 content: "\e230";
973 }
974 .glyphicon-ice-lolly:before {
975 content: "\e231";
976 }
977 .glyphicon-ice-lolly-tasted:before {
978 content: "\e232";
979 }
980 .glyphicon-education:before {
981 content: "\e233";
982 }
983 .glyphicon-option-horizontal:before {
984 content: "\e234";
985 }
986 .glyphicon-option-vertical:before {
987 content: "\e235";
988 }
989 .glyphicon-menu-hamburger:before {
990 content: "\e236";
991 }
992 .glyphicon-modal-window:before {
993 content: "\e237";
994 }
995 .glyphicon-oil:before {
996 content: "\e238";
997 }
998 .glyphicon-grain:before {
999 content: "\e239";
1000 }
1001 .glyphicon-sunglasses:before {
1002 content: "\e240";
1003 }
1004 .glyphicon-text-size:before {
1005 content: "\e241";
1006 }
1007 .glyphicon-text-color:before {
1008 content: "\e242";
1009 }
1010 .glyphicon-text-background:before {
1011 content: "\e243";
1012 }
1013 .glyphicon-object-align-top:before {
1014 content: "\e244";
1015 }
1016 .glyphicon-object-align-bottom:before {
1017 content: "\e245";
1018 }
1019 .glyphicon-object-align-horizontal:before {
1020 content: "\e246";
1021 }
1022 .glyphicon-object-align-left:before {
1023 content: "\e247";
1024 }
1025 .glyphicon-object-align-vertical:before {
1026 content: "\e248";
1027 }
1028 .glyphicon-object-align-right:before {
1029 content: "\e249";
1030 }
1031 .glyphicon-triangle-right:before {
1032 content: "\e250";
1033 }
1034 .glyphicon-triangle-left:before {
1035 content: "\e251";
1036 }
1037 .glyphicon-triangle-bottom:before {
1038 content: "\e252";
1039 }
1040 .glyphicon-triangle-top:before {
1041 content: "\e253";
1042 }
1043 .glyphicon-console:before {
1044 content: "\e254";
1045 }
1046 .glyphicon-superscript:before {
1047 content: "\e255";
1048 }
1049 .glyphicon-subscript:before {
1050 content: "\e256";
1051 }
1052 .glyphicon-menu-left:before {
1053 content: "\e257";
1054 }
1055 .glyphicon-menu-right:before {
1056 content: "\e258";
1057 }
1058 .glyphicon-menu-down:before {
1059 content: "\e259";
1060 }
1061 .glyphicon-menu-up:before {
1062 content: "\e260";
1063 }
1064 * {
1065 -webkit-box-sizing: border-box;
1066 -moz-box-sizing: border-box;
1067 box-sizing: border-box;
1068 }
1069 *:before,
1070 *:after {
1071 -webkit-box-sizing: border-box;
1072 -moz-box-sizing: border-box;
1073 box-sizing: border-box;
1074 }
1075 html {
1076 font-size: 10px;
1077 -webkit-tap-highlight-color: rgba(0, 0, 0, 0);
1078 }
1079 body {
1080 font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
1081 font-size: 13px;
1082 line-height: 1.42857143;
1083 color: #000;
1084 background-color: #fff;
1085 }
1086 input,
1087 button,
1088 select,
1089 textarea {
1090 font-family: inherit;
1091 font-size: inherit;
1092 line-height: inherit;
1093 }
1094 a {
1095 color: #337ab7;
1096 text-decoration: none;
1097 }
1098 a:hover,
1099 a:focus {
1100 color: #23527c;
1101 text-decoration: underline;
1102 }
1103 a:focus {
1104 outline: 5px auto -webkit-focus-ring-color;
1105 outline-offset: -2px;
1106 }
1107 figure {
1108 margin: 0;
1109 }
1110 img {
1111 vertical-align: middle;
1112 }
1113 .img-responsive,
1114 .thumbnail > img,
1115 .thumbnail a > img,
1116 .carousel-inner > .item > img,
1117 .carousel-inner > .item > a > img {
1118 display: block;
1119 max-width: 100%;
1120 height: auto;
1121 }
1122 .img-rounded {
1123 border-radius: 3px;
1124 }
1125 .img-thumbnail {
1126 padding: 4px;
1127 line-height: 1.42857143;
1128 background-color: #fff;
1129 border: 1px solid #ddd;
1130 border-radius: 2px;
1131 -webkit-transition: all 0.2s ease-in-out;
1132 -o-transition: all 0.2s ease-in-out;
1133 transition: all 0.2s ease-in-out;
1134 display: inline-block;
1135 max-width: 100%;
1136 height: auto;
1137 }
1138 .img-circle {
1139 border-radius: 50%;
1140 }
1141 hr {
1142 margin-top: 18px;
1143 margin-bottom: 18px;
1144 border: 0;
1145 border-top: 1px solid #eeeeee;
1146 }
1147 .sr-only {
1148 position: absolute;
1149 width: 1px;
1150 height: 1px;
1151 margin: -1px;
1152 padding: 0;
1153 overflow: hidden;
1154 clip: rect(0, 0, 0, 0);
1155 border: 0;
1156 }
1157 .sr-only-focusable:active,
1158 .sr-only-focusable:focus {
1159 position: static;
1160 width: auto;
1161 height: auto;
1162 margin: 0;
1163 overflow: visible;
1164 clip: auto;
1165 }
1166 [role="button"] {
1167 cursor: pointer;
1168 }
1169 h1,
1170 h2,
1171 h3,
1172 h4,
1173 h5,
1174 h6,
1175 .h1,
1176 .h2,
1177 .h3,
1178 .h4,
1179 .h5,
1180 .h6 {
1181 font-family: inherit;
1182 font-weight: 500;
1183 line-height: 1.1;
1184 color: inherit;
1185 }
1186 h1 small,
1187 h2 small,
1188 h3 small,
1189 h4 small,
1190 h5 small,
1191 h6 small,
1192 .h1 small,
1193 .h2 small,
1194 .h3 small,
1195 .h4 small,
1196 .h5 small,
1197 .h6 small,
1198 h1 .small,
1199 h2 .small,
1200 h3 .small,
1201 h4 .small,
1202 h5 .small,
1203 h6 .small,
1204 .h1 .small,
1205 .h2 .small,
1206 .h3 .small,
1207 .h4 .small,
1208 .h5 .small,
1209 .h6 .small {
1210 font-weight: normal;
1211 line-height: 1;
1212 color: #777777;
1213 }
1214 h1,
1215 .h1,
1216 h2,
1217 .h2,
1218 h3,
1219 .h3 {
1220 margin-top: 18px;
1221 margin-bottom: 9px;
1222 }
1223 h1 small,
1224 .h1 small,
1225 h2 small,
1226 .h2 small,
1227 h3 small,
1228 .h3 small,
1229 h1 .small,
1230 .h1 .small,
1231 h2 .small,
1232 .h2 .small,
1233 h3 .small,
1234 .h3 .small {
1235 font-size: 65%;
1236 }
1237 h4,
1238 .h4,
1239 h5,
1240 .h5,
1241 h6,
1242 .h6 {
1243 margin-top: 9px;
1244 margin-bottom: 9px;
1245 }
1246 h4 small,
1247 .h4 small,
1248 h5 small,
1249 .h5 small,
1250 h6 small,
1251 .h6 small,
1252 h4 .small,
1253 .h4 .small,
1254 h5 .small,
1255 .h5 .small,
1256 h6 .small,
1257 .h6 .small {
1258 font-size: 75%;
1259 }
1260 h1,
1261 .h1 {
1262 font-size: 33px;
1263 }
1264 h2,
1265 .h2 {
1266 font-size: 27px;
1267 }
1268 h3,
1269 .h3 {
1270 font-size: 23px;
1271 }
1272 h4,
1273 .h4 {
1274 font-size: 17px;
1275 }
1276 h5,
1277 .h5 {
1278 font-size: 13px;
1279 }
1280 h6,
1281 .h6 {
1282 font-size: 12px;
1283 }
1284 p {
1285 margin: 0 0 9px;
1286 }
1287 .lead {
1288 margin-bottom: 18px;
1289 font-size: 14px;
1290 font-weight: 300;
1291 line-height: 1.4;
1292 }
1293 @media (min-width: 768px) {
1294 .lead {
1295 font-size: 19.5px;
1296 }
1297 }
1298 small,
1299 .small {
1300 font-size: 92%;
1301 }
1302 mark,
1303 .mark {
1304 background-color: #fcf8e3;
1305 padding: .2em;
1306 }
1307 .text-left {
1308 text-align: left;
1309 }
1310 .text-right {
1311 text-align: right;
1312 }
1313 .text-center {
1314 text-align: center;
1315 }
1316 .text-justify {
1317 text-align: justify;
1318 }
1319 .text-nowrap {
1320 white-space: nowrap;
1321 }
1322 .text-lowercase {
1323 text-transform: lowercase;
1324 }
1325 .text-uppercase {
1326 text-transform: uppercase;
1327 }
1328 .text-capitalize {
1329 text-transform: capitalize;
1330 }
1331 .text-muted {
1332 color: #777777;
1333 }
1334 .text-primary {
1335 color: #337ab7;
1336 }
1337 a.text-primary:hover,
1338 a.text-primary:focus {
1339 color: #286090;
1340 }
1341 .text-success {
1342 color: #3c763d;
1343 }
1344 a.text-success:hover,
1345 a.text-success:focus {
1346 color: #2b542c;
1347 }
1348 .text-info {
1349 color: #31708f;
1350 }
1351 a.text-info:hover,
1352 a.text-info:focus {
1353 color: #245269;
1354 }
1355 .text-warning {
1356 color: #8a6d3b;
1357 }
1358 a.text-warning:hover,
1359 a.text-warning:focus {
1360 color: #66512c;
1361 }
1362 .text-danger {
1363 color: #a94442;
1364 }
1365 a.text-danger:hover,
1366 a.text-danger:focus {
1367 color: #843534;
1368 }
1369 .bg-primary {
1370 color: #fff;
1371 background-color: #337ab7;
1372 }
1373 a.bg-primary:hover,
1374 a.bg-primary:focus {
1375 background-color: #286090;
1376 }
1377 .bg-success {
1378 background-color: #dff0d8;
1379 }
1380 a.bg-success:hover,
1381 a.bg-success:focus {
1382 background-color: #c1e2b3;
1383 }
1384 .bg-info {
1385 background-color: #d9edf7;
1386 }
1387 a.bg-info:hover,
1388 a.bg-info:focus {
1389 background-color: #afd9ee;
1390 }
1391 .bg-warning {
1392 background-color: #fcf8e3;
1393 }
1394 a.bg-warning:hover,
1395 a.bg-warning:focus {
1396 background-color: #f7ecb5;
1397 }
1398 .bg-danger {
1399 background-color: #f2dede;
1400 }
1401 a.bg-danger:hover,
1402 a.bg-danger:focus {
1403 background-color: #e4b9b9;
1404 }
1405 .page-header {
1406 padding-bottom: 8px;
1407 margin: 36px 0 18px;
1408 border-bottom: 1px solid #eeeeee;
1409 }
1410 ul,
1411 ol {
1412 margin-top: 0;
1413 margin-bottom: 9px;
1414 }
1415 ul ul,
1416 ol ul,
1417 ul ol,
1418 ol ol {
1419 margin-bottom: 0;
1420 }
1421 .list-unstyled {
1422 padding-left: 0;
1423 list-style: none;
1424 }
1425 .list-inline {
1426 padding-left: 0;
1427 list-style: none;
1428 margin-left: -5px;
1429 }
1430 .list-inline > li {
1431 display: inline-block;
1432 padding-left: 5px;
1433 padding-right: 5px;
1434 }
1435 dl {
1436 margin-top: 0;
1437 margin-bottom: 18px;
1438 }
1439 dt,
1440 dd {
1441 line-height: 1.42857143;
1442 }
1443 dt {
1444 font-weight: bold;
1445 }
1446 dd {
1447 margin-left: 0;
1448 }
1449 @media (min-width: 541px) {
1450 .dl-horizontal dt {
1451 float: left;
1452 width: 160px;
1453 clear: left;
1454 text-align: right;
1455 overflow: hidden;
1456 text-overflow: ellipsis;
1457 white-space: nowrap;
1458 }
1459 .dl-horizontal dd {
1460 margin-left: 180px;
1461 }
1462 }
1463 abbr[title],
1464 abbr[data-original-title] {
1465 cursor: help;
1466 border-bottom: 1px dotted #777777;
1467 }
1468 .initialism {
1469 font-size: 90%;
1470 text-transform: uppercase;
1471 }
1472 blockquote {
1473 padding: 9px 18px;
1474 margin: 0 0 18px;
1475 font-size: inherit;
1476 border-left: 5px solid #eeeeee;
1477 }
1478 blockquote p:last-child,
1479 blockquote ul:last-child,
1480 blockquote ol:last-child {
1481 margin-bottom: 0;
1482 }
1483 blockquote footer,
1484 blockquote small,
1485 blockquote .small {
1486 display: block;
1487 font-size: 80%;
1488 line-height: 1.42857143;
1489 color: #777777;
1490 }
1491 blockquote footer:before,
1492 blockquote small:before,
1493 blockquote .small:before {
1494 content: '\2014 \00A0';
1495 }
1496 .blockquote-reverse,
1497 blockquote.pull-right {
1498 padding-right: 15px;
1499 padding-left: 0;
1500 border-right: 5px solid #eeeeee;
1501 border-left: 0;
1502 text-align: right;
1503 }
1504 .blockquote-reverse footer:before,
1505 blockquote.pull-right footer:before,
1506 .blockquote-reverse small:before,
1507 blockquote.pull-right small:before,
1508 .blockquote-reverse .small:before,
1509 blockquote.pull-right .small:before {
1510 content: '';
1511 }
1512 .blockquote-reverse footer:after,
1513 blockquote.pull-right footer:after,
1514 .blockquote-reverse small:after,
1515 blockquote.pull-right small:after,
1516 .blockquote-reverse .small:after,
1517 blockquote.pull-right .small:after {
1518 content: '\00A0 \2014';
1519 }
1520 address {
1521 margin-bottom: 18px;
1522 font-style: normal;
1523 line-height: 1.42857143;
1524 }
1525 code,
1526 kbd,
1527 pre,
1528 samp {
1529 font-family: monospace;
1530 }
1531 code {
1532 padding: 2px 4px;
1533 font-size: 90%;
1534 color: #c7254e;
1535 background-color: #f9f2f4;
1536 border-radius: 2px;
1537 }
1538 kbd {
1539 padding: 2px 4px;
1540 font-size: 90%;
1541 color: #888;
1542 background-color: transparent;
1543 border-radius: 1px;
1544 box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.25);
1545 }
1546 kbd kbd {
1547 padding: 0;
1548 font-size: 100%;
1549 font-weight: bold;
1550 box-shadow: none;
1551 }
1552 pre {
1553 display: block;
1554 padding: 8.5px;
1555 margin: 0 0 9px;
1556 font-size: 12px;
1557 line-height: 1.42857143;
1558 word-break: break-all;
1559 word-wrap: break-word;
1560 color: #333333;
1561 background-color: #f5f5f5;
1562 border: 1px solid #ccc;
1563 border-radius: 2px;
1564 }
1565 pre code {
1566 padding: 0;
1567 font-size: inherit;
1568 color: inherit;
1569 white-space: pre-wrap;
1570 background-color: transparent;
1571 border-radius: 0;
1572 }
1573 .pre-scrollable {
1574 max-height: 340px;
1575 overflow-y: scroll;
1576 }
1577 .container {
1578 margin-right: auto;
1579 margin-left: auto;
1580 padding-left: 0px;
1581 padding-right: 0px;
1582 }
1583 @media (min-width: 768px) {
1584 .container {
1585 width: 768px;
1586 }
1587 }
1588 @media (min-width: 992px) {
1589 .container {
1590 width: 940px;
1591 }
1592 }
1593 @media (min-width: 1200px) {
1594 .container {
1595 width: 1140px;
1596 }
1597 }
1598 .container-fluid {
1599 margin-right: auto;
1600 margin-left: auto;
1601 padding-left: 0px;
1602 padding-right: 0px;
1603 }
1604 .row {
1605 margin-left: 0px;
1606 margin-right: 0px;
1607 }
1608 .col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12 {
1609 position: relative;
1610 min-height: 1px;
1611 padding-left: 0px;
1612 padding-right: 0px;
1613 }
1614 .col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12 {
1615 float: left;
1616 }
1617 .col-xs-12 {
1618 width: 100%;
1619 }
1620 .col-xs-11 {
1621 width: 91.66666667%;
1622 }
1623 .col-xs-10 {
1624 width: 83.33333333%;
1625 }
1626 .col-xs-9 {
1627 width: 75%;
1628 }
1629 .col-xs-8 {
1630 width: 66.66666667%;
1631 }
1632 .col-xs-7 {
1633 width: 58.33333333%;
1634 }
1635 .col-xs-6 {
1636 width: 50%;
1637 }
1638 .col-xs-5 {
1639 width: 41.66666667%;
1640 }
1641 .col-xs-4 {
1642 width: 33.33333333%;
1643 }
1644 .col-xs-3 {
1645 width: 25%;
1646 }
1647 .col-xs-2 {
1648 width: 16.66666667%;
1649 }
1650 .col-xs-1 {
1651 width: 8.33333333%;
1652 }
1653 .col-xs-pull-12 {
1654 right: 100%;
1655 }
1656 .col-xs-pull-11 {
1657 right: 91.66666667%;
1658 }
1659 .col-xs-pull-10 {
1660 right: 83.33333333%;
1661 }
1662 .col-xs-pull-9 {
1663 right: 75%;
1664 }
1665 .col-xs-pull-8 {
1666 right: 66.66666667%;
1667 }
1668 .col-xs-pull-7 {
1669 right: 58.33333333%;
1670 }
1671 .col-xs-pull-6 {
1672 right: 50%;
1673 }
1674 .col-xs-pull-5 {
1675 right: 41.66666667%;
1676 }
1677 .col-xs-pull-4 {
1678 right: 33.33333333%;
1679 }
1680 .col-xs-pull-3 {
1681 right: 25%;
1682 }
1683 .col-xs-pull-2 {
1684 right: 16.66666667%;
1685 }
1686 .col-xs-pull-1 {
1687 right: 8.33333333%;
1688 }
1689 .col-xs-pull-0 {
1690 right: auto;
1691 }
1692 .col-xs-push-12 {
1693 left: 100%;
1694 }
1695 .col-xs-push-11 {
1696 left: 91.66666667%;
1697 }
1698 .col-xs-push-10 {
1699 left: 83.33333333%;
1700 }
1701 .col-xs-push-9 {
1702 left: 75%;
1703 }
1704 .col-xs-push-8 {
1705 left: 66.66666667%;
1706 }
1707 .col-xs-push-7 {
1708 left: 58.33333333%;
1709 }
1710 .col-xs-push-6 {
1711 left: 50%;
1712 }
1713 .col-xs-push-5 {
1714 left: 41.66666667%;
1715 }
1716 .col-xs-push-4 {
1717 left: 33.33333333%;
1718 }
1719 .col-xs-push-3 {
1720 left: 25%;
1721 }
1722 .col-xs-push-2 {
1723 left: 16.66666667%;
1724 }
1725 .col-xs-push-1 {
1726 left: 8.33333333%;
1727 }
1728 .col-xs-push-0 {
1729 left: auto;
1730 }
1731 .col-xs-offset-12 {
1732 margin-left: 100%;
1733 }
1734 .col-xs-offset-11 {
1735 margin-left: 91.66666667%;
1736 }
1737 .col-xs-offset-10 {
1738 margin-left: 83.33333333%;
1739 }
1740 .col-xs-offset-9 {
1741 margin-left: 75%;
1742 }
1743 .col-xs-offset-8 {
1744 margin-left: 66.66666667%;
1745 }
1746 .col-xs-offset-7 {
1747 margin-left: 58.33333333%;
1748 }
1749 .col-xs-offset-6 {
1750 margin-left: 50%;
1751 }
1752 .col-xs-offset-5 {
1753 margin-left: 41.66666667%;
1754 }
1755 .col-xs-offset-4 {
1756 margin-left: 33.33333333%;
1757 }
1758 .col-xs-offset-3 {
1759 margin-left: 25%;
1760 }
1761 .col-xs-offset-2 {
1762 margin-left: 16.66666667%;
1763 }
1764 .col-xs-offset-1 {
1765 margin-left: 8.33333333%;
1766 }
1767 .col-xs-offset-0 {
1768 margin-left: 0%;
1769 }
1770 @media (min-width: 768px) {
1771 .col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {
1772 float: left;
1773 }
1774 .col-sm-12 {
1775 width: 100%;
1776 }
1777 .col-sm-11 {
1778 width: 91.66666667%;
1779 }
1780 .col-sm-10 {
1781 width: 83.33333333%;
1782 }
1783 .col-sm-9 {
1784 width: 75%;
1785 }
1786 .col-sm-8 {
1787 width: 66.66666667%;
1788 }
1789 .col-sm-7 {
1790 width: 58.33333333%;
1791 }
1792 .col-sm-6 {
1793 width: 50%;
1794 }
1795 .col-sm-5 {
1796 width: 41.66666667%;
1797 }
1798 .col-sm-4 {
1799 width: 33.33333333%;
1800 }
1801 .col-sm-3 {
1802 width: 25%;
1803 }
1804 .col-sm-2 {
1805 width: 16.66666667%;
1806 }
1807 .col-sm-1 {
1808 width: 8.33333333%;
1809 }
1810 .col-sm-pull-12 {
1811 right: 100%;
1812 }
1813 .col-sm-pull-11 {
1814 right: 91.66666667%;
1815 }
1816 .col-sm-pull-10 {
1817 right: 83.33333333%;
1818 }
1819 .col-sm-pull-9 {
1820 right: 75%;
1821 }
1822 .col-sm-pull-8 {
1823 right: 66.66666667%;
1824 }
1825 .col-sm-pull-7 {
1826 right: 58.33333333%;
1827 }
1828 .col-sm-pull-6 {
1829 right: 50%;
1830 }
1831 .col-sm-pull-5 {
1832 right: 41.66666667%;
1833 }
1834 .col-sm-pull-4 {
1835 right: 33.33333333%;
1836 }
1837 .col-sm-pull-3 {
1838 right: 25%;
1839 }
1840 .col-sm-pull-2 {
1841 right: 16.66666667%;
1842 }
1843 .col-sm-pull-1 {
1844 right: 8.33333333%;
1845 }
1846 .col-sm-pull-0 {
1847 right: auto;
1848 }
1849 .col-sm-push-12 {
1850 left: 100%;
1851 }
1852 .col-sm-push-11 {
1853 left: 91.66666667%;
1854 }
1855 .col-sm-push-10 {
1856 left: 83.33333333%;
1857 }
1858 .col-sm-push-9 {
1859 left: 75%;
1860 }
1861 .col-sm-push-8 {
1862 left: 66.66666667%;
1863 }
1864 .col-sm-push-7 {
1865 left: 58.33333333%;
1866 }
1867 .col-sm-push-6 {
1868 left: 50%;
1869 }
1870 .col-sm-push-5 {
1871 left: 41.66666667%;
1872 }
1873 .col-sm-push-4 {
1874 left: 33.33333333%;
1875 }
1876 .col-sm-push-3 {
1877 left: 25%;
1878 }
1879 .col-sm-push-2 {
1880 left: 16.66666667%;
1881 }
1882 .col-sm-push-1 {
1883 left: 8.33333333%;
1884 }
1885 .col-sm-push-0 {
1886 left: auto;
1887 }
1888 .col-sm-offset-12 {
1889 margin-left: 100%;
1890 }
1891 .col-sm-offset-11 {
1892 margin-left: 91.66666667%;
1893 }
1894 .col-sm-offset-10 {
1895 margin-left: 83.33333333%;
1896 }
1897 .col-sm-offset-9 {
1898 margin-left: 75%;
1899 }
1900 .col-sm-offset-8 {
1901 margin-left: 66.66666667%;
1902 }
1903 .col-sm-offset-7 {
1904 margin-left: 58.33333333%;
1905 }
1906 .col-sm-offset-6 {
1907 margin-left: 50%;
1908 }
1909 .col-sm-offset-5 {
1910 margin-left: 41.66666667%;
1911 }
1912 .col-sm-offset-4 {
1913 margin-left: 33.33333333%;
1914 }
1915 .col-sm-offset-3 {
1916 margin-left: 25%;
1917 }
1918 .col-sm-offset-2 {
1919 margin-left: 16.66666667%;
1920 }
1921 .col-sm-offset-1 {
1922 margin-left: 8.33333333%;
1923 }
1924 .col-sm-offset-0 {
1925 margin-left: 0%;
1926 }
1927 }
1928 @media (min-width: 992px) {
1929 .col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12 {
1930 float: left;
1931 }
1932 .col-md-12 {
1933 width: 100%;
1934 }
1935 .col-md-11 {
1936 width: 91.66666667%;
1937 }
1938 .col-md-10 {
1939 width: 83.33333333%;
1940 }
1941 .col-md-9 {
1942 width: 75%;
1943 }
1944 .col-md-8 {
1945 width: 66.66666667%;
1946 }
1947 .col-md-7 {
1948 width: 58.33333333%;
1949 }
1950 .col-md-6 {
1951 width: 50%;
1952 }
1953 .col-md-5 {
1954 width: 41.66666667%;
1955 }
1956 .col-md-4 {
1957 width: 33.33333333%;
1958 }
1959 .col-md-3 {
1960 width: 25%;
1961 }
1962 .col-md-2 {
1963 width: 16.66666667%;
1964 }
1965 .col-md-1 {
1966 width: 8.33333333%;
1967 }
1968 .col-md-pull-12 {
1969 right: 100%;
1970 }
1971 .col-md-pull-11 {
1972 right: 91.66666667%;
1973 }
1974 .col-md-pull-10 {
1975 right: 83.33333333%;
1976 }
1977 .col-md-pull-9 {
1978 right: 75%;
1979 }
1980 .col-md-pull-8 {
1981 right: 66.66666667%;
1982 }
1983 .col-md-pull-7 {
1984 right: 58.33333333%;
1985 }
1986 .col-md-pull-6 {
1987 right: 50%;
1988 }
1989 .col-md-pull-5 {
1990 right: 41.66666667%;
1991 }
1992 .col-md-pull-4 {
1993 right: 33.33333333%;
1994 }
1995 .col-md-pull-3 {
1996 right: 25%;
1997 }
1998 .col-md-pull-2 {
1999 right: 16.66666667%;
2000 }
2001 .col-md-pull-1 {
2002 right: 8.33333333%;
2003 }
2004 .col-md-pull-0 {
2005 right: auto;
2006 }
2007 .col-md-push-12 {
2008 left: 100%;
2009 }
2010 .col-md-push-11 {
2011 left: 91.66666667%;
2012 }
2013 .col-md-push-10 {
2014 left: 83.33333333%;
2015 }
2016 .col-md-push-9 {
2017 left: 75%;
2018 }
2019 .col-md-push-8 {
2020 left: 66.66666667%;
2021 }
2022 .col-md-push-7 {
2023 left: 58.33333333%;
2024 }
2025 .col-md-push-6 {
2026 left: 50%;
2027 }
2028 .col-md-push-5 {
2029 left: 41.66666667%;
2030 }
2031 .col-md-push-4 {
2032 left: 33.33333333%;
2033 }
2034 .col-md-push-3 {
2035 left: 25%;
2036 }
2037 .col-md-push-2 {
2038 left: 16.66666667%;
2039 }
2040 .col-md-push-1 {
2041 left: 8.33333333%;
2042 }
2043 .col-md-push-0 {
2044 left: auto;
2045 }
2046 .col-md-offset-12 {
2047 margin-left: 100%;
2048 }
2049 .col-md-offset-11 {
2050 margin-left: 91.66666667%;
2051 }
2052 .col-md-offset-10 {
2053 margin-left: 83.33333333%;
2054 }
2055 .col-md-offset-9 {
2056 margin-left: 75%;
2057 }
2058 .col-md-offset-8 {
2059 margin-left: 66.66666667%;
2060 }
2061 .col-md-offset-7 {
2062 margin-left: 58.33333333%;
2063 }
2064 .col-md-offset-6 {
2065 margin-left: 50%;
2066 }
2067 .col-md-offset-5 {
2068 margin-left: 41.66666667%;
2069 }
2070 .col-md-offset-4 {
2071 margin-left: 33.33333333%;
2072 }
2073 .col-md-offset-3 {
2074 margin-left: 25%;
2075 }
2076 .col-md-offset-2 {
2077 margin-left: 16.66666667%;
2078 }
2079 .col-md-offset-1 {
2080 margin-left: 8.33333333%;
2081 }
2082 .col-md-offset-0 {
2083 margin-left: 0%;
2084 }
2085 }
2086 @media (min-width: 1200px) {
2087 .col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12 {
2088 float: left;
2089 }
2090 .col-lg-12 {
2091 width: 100%;
2092 }
2093 .col-lg-11 {
2094 width: 91.66666667%;
2095 }
2096 .col-lg-10 {
2097 width: 83.33333333%;
2098 }
2099 .col-lg-9 {
2100 width: 75%;
2101 }
2102 .col-lg-8 {
2103 width: 66.66666667%;
2104 }
2105 .col-lg-7 {
2106 width: 58.33333333%;
2107 }
2108 .col-lg-6 {
2109 width: 50%;
2110 }
2111 .col-lg-5 {
2112 width: 41.66666667%;
2113 }
2114 .col-lg-4 {
2115 width: 33.33333333%;
2116 }
2117 .col-lg-3 {
2118 width: 25%;
2119 }
2120 .col-lg-2 {
2121 width: 16.66666667%;
2122 }
2123 .col-lg-1 {
2124 width: 8.33333333%;
2125 }
2126 .col-lg-pull-12 {
2127 right: 100%;
2128 }
2129 .col-lg-pull-11 {
2130 right: 91.66666667%;
2131 }
2132 .col-lg-pull-10 {
2133 right: 83.33333333%;
2134 }
2135 .col-lg-pull-9 {
2136 right: 75%;
2137 }
2138 .col-lg-pull-8 {
2139 right: 66.66666667%;
2140 }
2141 .col-lg-pull-7 {
2142 right: 58.33333333%;
2143 }
2144 .col-lg-pull-6 {
2145 right: 50%;
2146 }
2147 .col-lg-pull-5 {
2148 right: 41.66666667%;
2149 }
2150 .col-lg-pull-4 {
2151 right: 33.33333333%;
2152 }
2153 .col-lg-pull-3 {
2154 right: 25%;
2155 }
2156 .col-lg-pull-2 {
2157 right: 16.66666667%;
2158 }
2159 .col-lg-pull-1 {
2160 right: 8.33333333%;
2161 }
2162 .col-lg-pull-0 {
2163 right: auto;
2164 }
2165 .col-lg-push-12 {
2166 left: 100%;
2167 }
2168 .col-lg-push-11 {
2169 left: 91.66666667%;
2170 }
2171 .col-lg-push-10 {
2172 left: 83.33333333%;
2173 }
2174 .col-lg-push-9 {
2175 left: 75%;
2176 }
2177 .col-lg-push-8 {
2178 left: 66.66666667%;
2179 }
2180 .col-lg-push-7 {
2181 left: 58.33333333%;
2182 }
2183 .col-lg-push-6 {
2184 left: 50%;
2185 }
2186 .col-lg-push-5 {
2187 left: 41.66666667%;
2188 }
2189 .col-lg-push-4 {
2190 left: 33.33333333%;
2191 }
2192 .col-lg-push-3 {
2193 left: 25%;
2194 }
2195 .col-lg-push-2 {
2196 left: 16.66666667%;
2197 }
2198 .col-lg-push-1 {
2199 left: 8.33333333%;
2200 }
2201 .col-lg-push-0 {
2202 left: auto;
2203 }
2204 .col-lg-offset-12 {
2205 margin-left: 100%;
2206 }
2207 .col-lg-offset-11 {
2208 margin-left: 91.66666667%;
2209 }
2210 .col-lg-offset-10 {
2211 margin-left: 83.33333333%;
2212 }
2213 .col-lg-offset-9 {
2214 margin-left: 75%;
2215 }
2216 .col-lg-offset-8 {
2217 margin-left: 66.66666667%;
2218 }
2219 .col-lg-offset-7 {
2220 margin-left: 58.33333333%;
2221 }
2222 .col-lg-offset-6 {
2223 margin-left: 50%;
2224 }
2225 .col-lg-offset-5 {
2226 margin-left: 41.66666667%;
2227 }
2228 .col-lg-offset-4 {
2229 margin-left: 33.33333333%;
2230 }
2231 .col-lg-offset-3 {
2232 margin-left: 25%;
2233 }
2234 .col-lg-offset-2 {
2235 margin-left: 16.66666667%;
2236 }
2237 .col-lg-offset-1 {
2238 margin-left: 8.33333333%;
2239 }
2240 .col-lg-offset-0 {
2241 margin-left: 0%;
2242 }
2243 }
2244 table {
2245 background-color: transparent;
2246 }
2247 caption {
2248 padding-top: 8px;
2249 padding-bottom: 8px;
2250 color: #777777;
2251 text-align: left;
2252 }
2253 th {
2254 text-align: left;
2255 }
2256 .table {
2257 width: 100%;
2258 max-width: 100%;
2259 margin-bottom: 18px;
2260 }
2261 .table > thead > tr > th,
2262 .table > tbody > tr > th,
2263 .table > tfoot > tr > th,
2264 .table > thead > tr > td,
2265 .table > tbody > tr > td,
2266 .table > tfoot > tr > td {
2267 padding: 8px;
2268 line-height: 1.42857143;
2269 vertical-align: top;
2270 border-top: 1px solid #ddd;
2271 }
2272 .table > thead > tr > th {
2273 vertical-align: bottom;
2274 border-bottom: 2px solid #ddd;
2275 }
2276 .table > caption + thead > tr:first-child > th,
2277 .table > colgroup + thead > tr:first-child > th,
2278 .table > thead:first-child > tr:first-child > th,
2279 .table > caption + thead > tr:first-child > td,
2280 .table > colgroup + thead > tr:first-child > td,
2281 .table > thead:first-child > tr:first-child > td {
2282 border-top: 0;
2283 }
2284 .table > tbody + tbody {
2285 border-top: 2px solid #ddd;
2286 }
2287 .table .table {
2288 background-color: #fff;
2289 }
2290 .table-condensed > thead > tr > th,
2291 .table-condensed > tbody > tr > th,
2292 .table-condensed > tfoot > tr > th,
2293 .table-condensed > thead > tr > td,
2294 .table-condensed > tbody > tr > td,
2295 .table-condensed > tfoot > tr > td {
2296 padding: 5px;
2297 }
2298 .table-bordered {
2299 border: 1px solid #ddd;
2300 }
2301 .table-bordered > thead > tr > th,
2302 .table-bordered > tbody > tr > th,
2303 .table-bordered > tfoot > tr > th,
2304 .table-bordered > thead > tr > td,
2305 .table-bordered > tbody > tr > td,
2306 .table-bordered > tfoot > tr > td {
2307 border: 1px solid #ddd;
2308 }
2309 .table-bordered > thead > tr > th,
2310 .table-bordered > thead > tr > td {
2311 border-bottom-width: 2px;
2312 }
2313 .table-striped > tbody > tr:nth-of-type(odd) {
2314 background-color: #f9f9f9;
2315 }
2316 .table-hover > tbody > tr:hover {
2317 background-color: #f5f5f5;
2318 }
2319 table col[class*="col-"] {
2320 position: static;
2321 float: none;
2322 display: table-column;
2323 }
2324 table td[class*="col-"],
2325 table th[class*="col-"] {
2326 position: static;
2327 float: none;
2328 display: table-cell;
2329 }
2330 .table > thead > tr > td.active,
2331 .table > tbody > tr > td.active,
2332 .table > tfoot > tr > td.active,
2333 .table > thead > tr > th.active,
2334 .table > tbody > tr > th.active,
2335 .table > tfoot > tr > th.active,
2336 .table > thead > tr.active > td,
2337 .table > tbody > tr.active > td,
2338 .table > tfoot > tr.active > td,
2339 .table > thead > tr.active > th,
2340 .table > tbody > tr.active > th,
2341 .table > tfoot > tr.active > th {
2342 background-color: #f5f5f5;
2343 }
2344 .table-hover > tbody > tr > td.active:hover,
2345 .table-hover > tbody > tr > th.active:hover,
2346 .table-hover > tbody > tr.active:hover > td,
2347 .table-hover > tbody > tr:hover > .active,
2348 .table-hover > tbody > tr.active:hover > th {
2349 background-color: #e8e8e8;
2350 }
2351 .table > thead > tr > td.success,
2352 .table > tbody > tr > td.success,
2353 .table > tfoot > tr > td.success,
2354 .table > thead > tr > th.success,
2355 .table > tbody > tr > th.success,
2356 .table > tfoot > tr > th.success,
2357 .table > thead > tr.success > td,
2358 .table > tbody > tr.success > td,
2359 .table > tfoot > tr.success > td,
2360 .table > thead > tr.success > th,
2361 .table > tbody > tr.success > th,
2362 .table > tfoot > tr.success > th {
2363 background-color: #dff0d8;
2364 }
2365 .table-hover > tbody > tr > td.success:hover,
2366 .table-hover > tbody > tr > th.success:hover,
2367 .table-hover > tbody > tr.success:hover > td,
2368 .table-hover > tbody > tr:hover > .success,
2369 .table-hover > tbody > tr.success:hover > th {
2370 background-color: #d0e9c6;
2371 }
2372 .table > thead > tr > td.info,
2373 .table > tbody > tr > td.info,
2374 .table > tfoot > tr > td.info,
2375 .table > thead > tr > th.info,
2376 .table > tbody > tr > th.info,
2377 .table > tfoot > tr > th.info,
2378 .table > thead > tr.info > td,
2379 .table > tbody > tr.info > td,
2380 .table > tfoot > tr.info > td,
2381 .table > thead > tr.info > th,
2382 .table > tbody > tr.info > th,
2383 .table > tfoot > tr.info > th {
2384 background-color: #d9edf7;
2385 }
2386 .table-hover > tbody > tr > td.info:hover,
2387 .table-hover > tbody > tr > th.info:hover,
2388 .table-hover > tbody > tr.info:hover > td,
2389 .table-hover > tbody > tr:hover > .info,
2390 .table-hover > tbody > tr.info:hover > th {
2391 background-color: #c4e3f3;
2392 }
2393 .table > thead > tr > td.warning,
2394 .table > tbody > tr > td.warning,
2395 .table > tfoot > tr > td.warning,
2396 .table > thead > tr > th.warning,
2397 .table > tbody > tr > th.warning,
2398 .table > tfoot > tr > th.warning,
2399 .table > thead > tr.warning > td,
2400 .table > tbody > tr.warning > td,
2401 .table > tfoot > tr.warning > td,
2402 .table > thead > tr.warning > th,
2403 .table > tbody > tr.warning > th,
2404 .table > tfoot > tr.warning > th {
2405 background-color: #fcf8e3;
2406 }
2407 .table-hover > tbody > tr > td.warning:hover,
2408 .table-hover > tbody > tr > th.warning:hover,
2409 .table-hover > tbody > tr.warning:hover > td,
2410 .table-hover > tbody > tr:hover > .warning,
2411 .table-hover > tbody > tr.warning:hover > th {
2412 background-color: #faf2cc;
2413 }
2414 .table > thead > tr > td.danger,
2415 .table > tbody > tr > td.danger,
2416 .table > tfoot > tr > td.danger,
2417 .table > thead > tr > th.danger,
2418 .table > tbody > tr > th.danger,
2419 .table > tfoot > tr > th.danger,
2420 .table > thead > tr.danger > td,
2421 .table > tbody > tr.danger > td,
2422 .table > tfoot > tr.danger > td,
2423 .table > thead > tr.danger > th,
2424 .table > tbody > tr.danger > th,
2425 .table > tfoot > tr.danger > th {
2426 background-color: #f2dede;
2427 }
2428 .table-hover > tbody > tr > td.danger:hover,
2429 .table-hover > tbody > tr > th.danger:hover,
2430 .table-hover > tbody > tr.danger:hover > td,
2431 .table-hover > tbody > tr:hover > .danger,
2432 .table-hover > tbody > tr.danger:hover > th {
2433 background-color: #ebcccc;
2434 }
2435 .table-responsive {
2436 overflow-x: auto;
2437 min-height: 0.01%;
2438 }
2439 @media screen and (max-width: 767px) {
2440 .table-responsive {
2441 width: 100%;
2442 margin-bottom: 13.5px;
2443 overflow-y: hidden;
2444 -ms-overflow-style: -ms-autohiding-scrollbar;
2445 border: 1px solid #ddd;
2446 }
2447 .table-responsive > .table {
2448 margin-bottom: 0;
2449 }
2450 .table-responsive > .table > thead > tr > th,
2451 .table-responsive > .table > tbody > tr > th,
2452 .table-responsive > .table > tfoot > tr > th,
2453 .table-responsive > .table > thead > tr > td,
2454 .table-responsive > .table > tbody > tr > td,
2455 .table-responsive > .table > tfoot > tr > td {
2456 white-space: nowrap;
2457 }
2458 .table-responsive > .table-bordered {
2459 border: 0;
2460 }
2461 .table-responsive > .table-bordered > thead > tr > th:first-child,
2462 .table-responsive > .table-bordered > tbody > tr > th:first-child,
2463 .table-responsive > .table-bordered > tfoot > tr > th:first-child,
2464 .table-responsive > .table-bordered > thead > tr > td:first-child,
2465 .table-responsive > .table-bordered > tbody > tr > td:first-child,
2466 .table-responsive > .table-bordered > tfoot > tr > td:first-child {
2467 border-left: 0;
2468 }
2469 .table-responsive > .table-bordered > thead > tr > th:last-child,
2470 .table-responsive > .table-bordered > tbody > tr > th:last-child,
2471 .table-responsive > .table-bordered > tfoot > tr > th:last-child,
2472 .table-responsive > .table-bordered > thead > tr > td:last-child,
2473 .table-responsive > .table-bordered > tbody > tr > td:last-child,
2474 .table-responsive > .table-bordered > tfoot > tr > td:last-child {
2475 border-right: 0;
2476 }
2477 .table-responsive > .table-bordered > tbody > tr:last-child > th,
2478 .table-responsive > .table-bordered > tfoot > tr:last-child > th,
2479 .table-responsive > .table-bordered > tbody > tr:last-child > td,
2480 .table-responsive > .table-bordered > tfoot > tr:last-child > td {
2481 border-bottom: 0;
2482 }
2483 }
2484 fieldset {
2485 padding: 0;
2486 margin: 0;
2487 border: 0;
2488 min-width: 0;
2489 }
2490 legend {
2491 display: block;
2492 width: 100%;
2493 padding: 0;
2494 margin-bottom: 18px;
2495 font-size: 19.5px;
2496 line-height: inherit;
2497 color: #333333;
2498 border: 0;
2499 border-bottom: 1px solid #e5e5e5;
2500 }
2501 label {
2502 display: inline-block;
2503 max-width: 100%;
2504 margin-bottom: 5px;
2505 font-weight: bold;
2506 }
2507 input[type="search"] {
2508 -webkit-box-sizing: border-box;
2509 -moz-box-sizing: border-box;
2510 box-sizing: border-box;
2511 }
2512 input[type="radio"],
2513 input[type="checkbox"] {
2514 margin: 4px 0 0;
2515 margin-top: 1px \9;
2516 line-height: normal;
2517 }
2518 input[type="file"] {
2519 display: block;
2520 }
2521 input[type="range"] {
2522 display: block;
2523 width: 100%;
2524 }
2525 select[multiple],
2526 select[size] {
2527 height: auto;
2528 }
2529 input[type="file"]:focus,
2530 input[type="radio"]:focus,
2531 input[type="checkbox"]:focus {
2532 outline: 5px auto -webkit-focus-ring-color;
2533 outline-offset: -2px;
2534 }
2535 output {
2536 display: block;
2537 padding-top: 7px;
2538 font-size: 13px;
2539 line-height: 1.42857143;
2540 color: #555555;
2541 }
2542 .form-control {
2543 display: block;
2544 width: 100%;
2545 height: 32px;
2546 padding: 6px 12px;
2547 font-size: 13px;
2548 line-height: 1.42857143;
2549 color: #555555;
2550 background-color: #fff;
2551 background-image: none;
2552 border: 1px solid #ccc;
2553 border-radius: 2px;
2554 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2555 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2556 -webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
2557 -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
2558 transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
2559 }
2560 .form-control:focus {
2561 border-color: #66afe9;
2562 outline: 0;
2563 -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
2564 box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
2565 }
2566 .form-control::-moz-placeholder {
2567 color: #999;
2568 opacity: 1;
2569 }
2570 .form-control:-ms-input-placeholder {
2571 color: #999;
2572 }
2573 .form-control::-webkit-input-placeholder {
2574 color: #999;
2575 }
2576 .form-control::-ms-expand {
2577 border: 0;
2578 background-color: transparent;
2579 }
2580 .form-control[disabled],
2581 .form-control[readonly],
2582 fieldset[disabled] .form-control {
2583 background-color: #eeeeee;
2584 opacity: 1;
2585 }
2586 .form-control[disabled],
2587 fieldset[disabled] .form-control {
2588 cursor: not-allowed;
2589 }
2590 textarea.form-control {
2591 height: auto;
2592 }
2593 input[type="search"] {
2594 -webkit-appearance: none;
2595 }
2596 @media screen and (-webkit-min-device-pixel-ratio: 0) {
2597 input[type="date"].form-control,
2598 input[type="time"].form-control,
2599 input[type="datetime-local"].form-control,
2600 input[type="month"].form-control {
2601 line-height: 32px;
2602 }
2603 input[type="date"].input-sm,
2604 input[type="time"].input-sm,
2605 input[type="datetime-local"].input-sm,
2606 input[type="month"].input-sm,
2607 .input-group-sm input[type="date"],
2608 .input-group-sm input[type="time"],
2609 .input-group-sm input[type="datetime-local"],
2610 .input-group-sm input[type="month"] {
2611 line-height: 30px;
2612 }
2613 input[type="date"].input-lg,
2614 input[type="time"].input-lg,
2615 input[type="datetime-local"].input-lg,
2616 input[type="month"].input-lg,
2617 .input-group-lg input[type="date"],
2618 .input-group-lg input[type="time"],
2619 .input-group-lg input[type="datetime-local"],
2620 .input-group-lg input[type="month"] {
2621 line-height: 45px;
2622 }
2623 }
2624 .form-group {
2625 margin-bottom: 15px;
2626 }
2627 .radio,
2628 .checkbox {
2629 position: relative;
2630 display: block;
2631 margin-top: 10px;
2632 margin-bottom: 10px;
2633 }
2634 .radio label,
2635 .checkbox label {
2636 min-height: 18px;
2637 padding-left: 20px;
2638 margin-bottom: 0;
2639 font-weight: normal;
2640 cursor: pointer;
2641 }
2642 .radio input[type="radio"],
2643 .radio-inline input[type="radio"],
2644 .checkbox input[type="checkbox"],
2645 .checkbox-inline input[type="checkbox"] {
2646 position: absolute;
2647 margin-left: -20px;
2648 margin-top: 4px \9;
2649 }
2650 .radio + .radio,
2651 .checkbox + .checkbox {
2652 margin-top: -5px;
2653 }
2654 .radio-inline,
2655 .checkbox-inline {
2656 position: relative;
2657 display: inline-block;
2658 padding-left: 20px;
2659 margin-bottom: 0;
2660 vertical-align: middle;
2661 font-weight: normal;
2662 cursor: pointer;
2663 }
2664 .radio-inline + .radio-inline,
2665 .checkbox-inline + .checkbox-inline {
2666 margin-top: 0;
2667 margin-left: 10px;
2668 }
2669 input[type="radio"][disabled],
2670 input[type="checkbox"][disabled],
2671 input[type="radio"].disabled,
2672 input[type="checkbox"].disabled,
2673 fieldset[disabled] input[type="radio"],
2674 fieldset[disabled] input[type="checkbox"] {
2675 cursor: not-allowed;
2676 }
2677 .radio-inline.disabled,
2678 .checkbox-inline.disabled,
2679 fieldset[disabled] .radio-inline,
2680 fieldset[disabled] .checkbox-inline {
2681 cursor: not-allowed;
2682 }
2683 .radio.disabled label,
2684 .checkbox.disabled label,
2685 fieldset[disabled] .radio label,
2686 fieldset[disabled] .checkbox label {
2687 cursor: not-allowed;
2688 }
2689 .form-control-static {
2690 padding-top: 7px;
2691 padding-bottom: 7px;
2692 margin-bottom: 0;
2693 min-height: 31px;
2694 }
2695 .form-control-static.input-lg,
2696 .form-control-static.input-sm {
2697 padding-left: 0;
2698 padding-right: 0;
2699 }
2700 .input-sm {
2701 height: 30px;
2702 padding: 5px 10px;
2703 font-size: 12px;
2704 line-height: 1.5;
2705 border-radius: 1px;
2706 }
2707 select.input-sm {
2708 height: 30px;
2709 line-height: 30px;
2710 }
2711 textarea.input-sm,
2712 select[multiple].input-sm {
2713 height: auto;
2714 }
2715 .form-group-sm .form-control {
2716 height: 30px;
2717 padding: 5px 10px;
2718 font-size: 12px;
2719 line-height: 1.5;
2720 border-radius: 1px;
2721 }
2722 .form-group-sm select.form-control {
2723 height: 30px;
2724 line-height: 30px;
2725 }
2726 .form-group-sm textarea.form-control,
2727 .form-group-sm select[multiple].form-control {
2728 height: auto;
2729 }
2730 .form-group-sm .form-control-static {
2731 height: 30px;
2732 min-height: 30px;
2733 padding: 6px 10px;
2734 font-size: 12px;
2735 line-height: 1.5;
2736 }
2737 .input-lg {
2738 height: 45px;
2739 padding: 10px 16px;
2740 font-size: 17px;
2741 line-height: 1.3333333;
2742 border-radius: 3px;
2743 }
2744 select.input-lg {
2745 height: 45px;
2746 line-height: 45px;
2747 }
2748 textarea.input-lg,
2749 select[multiple].input-lg {
2750 height: auto;
2751 }
2752 .form-group-lg .form-control {
2753 height: 45px;
2754 padding: 10px 16px;
2755 font-size: 17px;
2756 line-height: 1.3333333;
2757 border-radius: 3px;
2758 }
2759 .form-group-lg select.form-control {
2760 height: 45px;
2761 line-height: 45px;
2762 }
2763 .form-group-lg textarea.form-control,
2764 .form-group-lg select[multiple].form-control {
2765 height: auto;
2766 }
2767 .form-group-lg .form-control-static {
2768 height: 45px;
2769 min-height: 35px;
2770 padding: 11px 16px;
2771 font-size: 17px;
2772 line-height: 1.3333333;
2773 }
2774 .has-feedback {
2775 position: relative;
2776 }
2777 .has-feedback .form-control {
2778 padding-right: 40px;
2779 }
2780 .form-control-feedback {
2781 position: absolute;
2782 top: 0;
2783 right: 0;
2784 z-index: 2;
2785 display: block;
2786 width: 32px;
2787 height: 32px;
2788 line-height: 32px;
2789 text-align: center;
2790 pointer-events: none;
2791 }
2792 .input-lg + .form-control-feedback,
2793 .input-group-lg + .form-control-feedback,
2794 .form-group-lg .form-control + .form-control-feedback {
2795 width: 45px;
2796 height: 45px;
2797 line-height: 45px;
2798 }
2799 .input-sm + .form-control-feedback,
2800 .input-group-sm + .form-control-feedback,
2801 .form-group-sm .form-control + .form-control-feedback {
2802 width: 30px;
2803 height: 30px;
2804 line-height: 30px;
2805 }
2806 .has-success .help-block,
2807 .has-success .control-label,
2808 .has-success .radio,
2809 .has-success .checkbox,
2810 .has-success .radio-inline,
2811 .has-success .checkbox-inline,
2812 .has-success.radio label,
2813 .has-success.checkbox label,
2814 .has-success.radio-inline label,
2815 .has-success.checkbox-inline label {
2816 color: #3c763d;
2817 }
2818 .has-success .form-control {
2819 border-color: #3c763d;
2820 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2821 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2822 }
2823 .has-success .form-control:focus {
2824 border-color: #2b542c;
2825 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #67b168;
2826 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #67b168;
2827 }
2828 .has-success .input-group-addon {
2829 color: #3c763d;
2830 border-color: #3c763d;
2831 background-color: #dff0d8;
2832 }
2833 .has-success .form-control-feedback {
2834 color: #3c763d;
2835 }
2836 .has-warning .help-block,
2837 .has-warning .control-label,
2838 .has-warning .radio,
2839 .has-warning .checkbox,
2840 .has-warning .radio-inline,
2841 .has-warning .checkbox-inline,
2842 .has-warning.radio label,
2843 .has-warning.checkbox label,
2844 .has-warning.radio-inline label,
2845 .has-warning.checkbox-inline label {
2846 color: #8a6d3b;
2847 }
2848 .has-warning .form-control {
2849 border-color: #8a6d3b;
2850 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2851 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2852 }
2853 .has-warning .form-control:focus {
2854 border-color: #66512c;
2855 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #c0a16b;
2856 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #c0a16b;
2857 }
2858 .has-warning .input-group-addon {
2859 color: #8a6d3b;
2860 border-color: #8a6d3b;
2861 background-color: #fcf8e3;
2862 }
2863 .has-warning .form-control-feedback {
2864 color: #8a6d3b;
2865 }
2866 .has-error .help-block,
2867 .has-error .control-label,
2868 .has-error .radio,
2869 .has-error .checkbox,
2870 .has-error .radio-inline,
2871 .has-error .checkbox-inline,
2872 .has-error.radio label,
2873 .has-error.checkbox label,
2874 .has-error.radio-inline label,
2875 .has-error.checkbox-inline label {
2876 color: #a94442;
2877 }
2878 .has-error .form-control {
2879 border-color: #a94442;
2880 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2881 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
2882 }
2883 .has-error .form-control:focus {
2884 border-color: #843534;
2885 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #ce8483;
2886 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 6px #ce8483;
2887 }
2888 .has-error .input-group-addon {
2889 color: #a94442;
2890 border-color: #a94442;
2891 background-color: #f2dede;
2892 }
2893 .has-error .form-control-feedback {
2894 color: #a94442;
2895 }
2896 .has-feedback label ~ .form-control-feedback {
2897 top: 23px;
2898 }
2899 .has-feedback label.sr-only ~ .form-control-feedback {
2900 top: 0;
2901 }
2902 .help-block {
2903 display: block;
2904 margin-top: 5px;
2905 margin-bottom: 10px;
2906 color: #404040;
2907 }
2908 @media (min-width: 768px) {
2909 .form-inline .form-group {
2910 display: inline-block;
2911 margin-bottom: 0;
2912 vertical-align: middle;
2913 }
2914 .form-inline .form-control {
2915 display: inline-block;
2916 width: auto;
2917 vertical-align: middle;
2918 }
2919 .form-inline .form-control-static {
2920 display: inline-block;
2921 }
2922 .form-inline .input-group {
2923 display: inline-table;
2924 vertical-align: middle;
2925 }
2926 .form-inline .input-group .input-group-addon,
2927 .form-inline .input-group .input-group-btn,
2928 .form-inline .input-group .form-control {
2929 width: auto;
2930 }
2931 .form-inline .input-group > .form-control {
2932 width: 100%;
2933 }
2934 .form-inline .control-label {
2935 margin-bottom: 0;
2936 vertical-align: middle;
2937 }
2938 .form-inline .radio,
2939 .form-inline .checkbox {
2940 display: inline-block;
2941 margin-top: 0;
2942 margin-bottom: 0;
2943 vertical-align: middle;
2944 }
2945 .form-inline .radio label,
2946 .form-inline .checkbox label {
2947 padding-left: 0;
2948 }
2949 .form-inline .radio input[type="radio"],
2950 .form-inline .checkbox input[type="checkbox"] {
2951 position: relative;
2952 margin-left: 0;
2953 }
2954 .form-inline .has-feedback .form-control-feedback {
2955 top: 0;
2956 }
2957 }
2958 .form-horizontal .radio,
2959 .form-horizontal .checkbox,
2960 .form-horizontal .radio-inline,
2961 .form-horizontal .checkbox-inline {
2962 margin-top: 0;
2963 margin-bottom: 0;
2964 padding-top: 7px;
2965 }
2966 .form-horizontal .radio,
2967 .form-horizontal .checkbox {
2968 min-height: 25px;
2969 }
2970 .form-horizontal .form-group {
2971 margin-left: 0px;
2972 margin-right: 0px;
2973 }
2974 @media (min-width: 768px) {
2975 .form-horizontal .control-label {
2976 text-align: right;
2977 margin-bottom: 0;
2978 padding-top: 7px;
2979 }
2980 }
2981 .form-horizontal .has-feedback .form-control-feedback {
2982 right: 0px;
2983 }
2984 @media (min-width: 768px) {
2985 .form-horizontal .form-group-lg .control-label {
2986 padding-top: 11px;
2987 font-size: 17px;
2988 }
2989 }
2990 @media (min-width: 768px) {
2991 .form-horizontal .form-group-sm .control-label {
2992 padding-top: 6px;
2993 font-size: 12px;
2994 }
2995 }
2996 .btn {
2997 display: inline-block;
2998 margin-bottom: 0;
2999 font-weight: normal;
3000 text-align: center;
3001 vertical-align: middle;
3002 touch-action: manipulation;
3003 cursor: pointer;
3004 background-image: none;
3005 border: 1px solid transparent;
3006 white-space: nowrap;
3007 padding: 6px 12px;
3008 font-size: 13px;
3009 line-height: 1.42857143;
3010 border-radius: 2px;
3011 -webkit-user-select: none;
3012 -moz-user-select: none;
3013 -ms-user-select: none;
3014 user-select: none;
3015 }
3016 .btn:focus,
3017 .btn:active:focus,
3018 .btn.active:focus,
3019 .btn.focus,
3020 .btn:active.focus,
3021 .btn.active.focus {
3022 outline: 5px auto -webkit-focus-ring-color;
3023 outline-offset: -2px;
3024 }
3025 .btn:hover,
3026 .btn:focus,
3027 .btn.focus {
3028 color: #333;
3029 text-decoration: none;
3030 }
3031 .btn:active,
3032 .btn.active {
3033 outline: 0;
3034 background-image: none;
3035 -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
3036 box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
3037 }
3038 .btn.disabled,
3039 .btn[disabled],
3040 fieldset[disabled] .btn {
3041 cursor: not-allowed;
3042 opacity: 0.65;
3043 filter: alpha(opacity=65);
3044 -webkit-box-shadow: none;
3045 box-shadow: none;
3046 }
3047 a.btn.disabled,
3048 fieldset[disabled] a.btn {
3049 pointer-events: none;
3050 }
3051 .btn-default {
3052 color: #333;
3053 background-color: #fff;
3054 border-color: #ccc;
3055 }
3056 .btn-default:focus,
3057 .btn-default.focus {
3058 color: #333;
3059 background-color: #e6e6e6;
3060 border-color: #8c8c8c;
3061 }
3062 .btn-default:hover {
3063 color: #333;
3064 background-color: #e6e6e6;
3065 border-color: #adadad;
3066 }
3067 .btn-default:active,
3068 .btn-default.active,
3069 .open > .dropdown-toggle.btn-default {
3070 color: #333;
3071 background-color: #e6e6e6;
3072 border-color: #adadad;
3073 }
3074 .btn-default:active:hover,
3075 .btn-default.active:hover,
3076 .open > .dropdown-toggle.btn-default:hover,
3077 .btn-default:active:focus,
3078 .btn-default.active:focus,
3079 .open > .dropdown-toggle.btn-default:focus,
3080 .btn-default:active.focus,
3081 .btn-default.active.focus,
3082 .open > .dropdown-toggle.btn-default.focus {
3083 color: #333;
3084 background-color: #d4d4d4;
3085 border-color: #8c8c8c;
3086 }
3087 .btn-default:active,
3088 .btn-default.active,
3089 .open > .dropdown-toggle.btn-default {
3090 background-image: none;
3091 }
3092 .btn-default.disabled:hover,
3093 .btn-default[disabled]:hover,
3094 fieldset[disabled] .btn-default:hover,
3095 .btn-default.disabled:focus,
3096 .btn-default[disabled]:focus,
3097 fieldset[disabled] .btn-default:focus,
3098 .btn-default.disabled.focus,
3099 .btn-default[disabled].focus,
3100 fieldset[disabled] .btn-default.focus {
3101 background-color: #fff;
3102 border-color: #ccc;
3103 }
3104 .btn-default .badge {
3105 color: #fff;
3106 background-color: #333;
3107 }
3108 .btn-primary {
3109 color: #fff;
3110 background-color: #337ab7;
3111 border-color: #2e6da4;
3112 }
3113 .btn-primary:focus,
3114 .btn-primary.focus {
3115 color: #fff;
3116 background-color: #286090;
3117 border-color: #122b40;
3118 }
3119 .btn-primary:hover {
3120 color: #fff;
3121 background-color: #286090;
3122 border-color: #204d74;
3123 }
3124 .btn-primary:active,
3125 .btn-primary.active,
3126 .open > .dropdown-toggle.btn-primary {
3127 color: #fff;
3128 background-color: #286090;
3129 border-color: #204d74;
3130 }
3131 .btn-primary:active:hover,
3132 .btn-primary.active:hover,
3133 .open > .dropdown-toggle.btn-primary:hover,
3134 .btn-primary:active:focus,
3135 .btn-primary.active:focus,
3136 .open > .dropdown-toggle.btn-primary:focus,
3137 .btn-primary:active.focus,
3138 .btn-primary.active.focus,
3139 .open > .dropdown-toggle.btn-primary.focus {
3140 color: #fff;
3141 background-color: #204d74;
3142 border-color: #122b40;
3143 }
3144 .btn-primary:active,
3145 .btn-primary.active,
3146 .open > .dropdown-toggle.btn-primary {
3147 background-image: none;
3148 }
3149 .btn-primary.disabled:hover,
3150 .btn-primary[disabled]:hover,
3151 fieldset[disabled] .btn-primary:hover,
3152 .btn-primary.disabled:focus,
3153 .btn-primary[disabled]:focus,
3154 fieldset[disabled] .btn-primary:focus,
3155 .btn-primary.disabled.focus,
3156 .btn-primary[disabled].focus,
3157 fieldset[disabled] .btn-primary.focus {
3158 background-color: #337ab7;
3159 border-color: #2e6da4;
3160 }
3161 .btn-primary .badge {
3162 color: #337ab7;
3163 background-color: #fff;
3164 }
3165 .btn-success {
3166 color: #fff;
3167 background-color: #5cb85c;
3168 border-color: #4cae4c;
3169 }
3170 .btn-success:focus,
3171 .btn-success.focus {
3172 color: #fff;
3173 background-color: #449d44;
3174 border-color: #255625;
3175 }
3176 .btn-success:hover {
3177 color: #fff;
3178 background-color: #449d44;
3179 border-color: #398439;
3180 }
3181 .btn-success:active,
3182 .btn-success.active,
3183 .open > .dropdown-toggle.btn-success {
3184 color: #fff;
3185 background-color: #449d44;
3186 border-color: #398439;
3187 }
3188 .btn-success:active:hover,
3189 .btn-success.active:hover,
3190 .open > .dropdown-toggle.btn-success:hover,
3191 .btn-success:active:focus,
3192 .btn-success.active:focus,
3193 .open > .dropdown-toggle.btn-success:focus,
3194 .btn-success:active.focus,
3195 .btn-success.active.focus,
3196 .open > .dropdown-toggle.btn-success.focus {
3197 color: #fff;
3198 background-color: #398439;
3199 border-color: #255625;
3200 }
3201 .btn-success:active,
3202 .btn-success.active,
3203 .open > .dropdown-toggle.btn-success {
3204 background-image: none;
3205 }
3206 .btn-success.disabled:hover,
3207 .btn-success[disabled]:hover,
3208 fieldset[disabled] .btn-success:hover,
3209 .btn-success.disabled:focus,
3210 .btn-success[disabled]:focus,
3211 fieldset[disabled] .btn-success:focus,
3212 .btn-success.disabled.focus,
3213 .btn-success[disabled].focus,
3214 fieldset[disabled] .btn-success.focus {
3215 background-color: #5cb85c;
3216 border-color: #4cae4c;
3217 }
3218 .btn-success .badge {
3219 color: #5cb85c;
3220 background-color: #fff;
3221 }
3222 .btn-info {
3223 color: #fff;
3224 background-color: #5bc0de;
3225 border-color: #46b8da;
3226 }
3227 .btn-info:focus,
3228 .btn-info.focus {
3229 color: #fff;
3230 background-color: #31b0d5;
3231 border-color: #1b6d85;
3232 }
3233 .btn-info:hover {
3234 color: #fff;
3235 background-color: #31b0d5;
3236 border-color: #269abc;
3237 }
3238 .btn-info:active,
3239 .btn-info.active,
3240 .open > .dropdown-toggle.btn-info {
3241 color: #fff;
3242 background-color: #31b0d5;
3243 border-color: #269abc;
3244 }
3245 .btn-info:active:hover,
3246 .btn-info.active:hover,
3247 .open > .dropdown-toggle.btn-info:hover,
3248 .btn-info:active:focus,
3249 .btn-info.active:focus,
3250 .open > .dropdown-toggle.btn-info:focus,
3251 .btn-info:active.focus,
3252 .btn-info.active.focus,
3253 .open > .dropdown-toggle.btn-info.focus {
3254 color: #fff;
3255 background-color: #269abc;
3256 border-color: #1b6d85;
3257 }
3258 .btn-info:active,
3259 .btn-info.active,
3260 .open > .dropdown-toggle.btn-info {
3261 background-image: none;
3262 }
3263 .btn-info.disabled:hover,
3264 .btn-info[disabled]:hover,
3265 fieldset[disabled] .btn-info:hover,
3266 .btn-info.disabled:focus,
3267 .btn-info[disabled]:focus,
3268 fieldset[disabled] .btn-info:focus,
3269 .btn-info.disabled.focus,
3270 .btn-info[disabled].focus,
3271 fieldset[disabled] .btn-info.focus {
3272 background-color: #5bc0de;
3273 border-color: #46b8da;
3274 }
3275 .btn-info .badge {
3276 color: #5bc0de;
3277 background-color: #fff;
3278 }
3279 .btn-warning {
3280 color: #fff;
3281 background-color: #f0ad4e;
3282 border-color: #eea236;
3283 }
3284 .btn-warning:focus,
3285 .btn-warning.focus {
3286 color: #fff;
3287 background-color: #ec971f;
3288 border-color: #985f0d;
3289 }
3290 .btn-warning:hover {
3291 color: #fff;
3292 background-color: #ec971f;
3293 border-color: #d58512;
3294 }
3295 .btn-warning:active,
3296 .btn-warning.active,
3297 .open > .dropdown-toggle.btn-warning {
3298 color: #fff;
3299 background-color: #ec971f;
3300 border-color: #d58512;
3301 }
3302 .btn-warning:active:hover,
3303 .btn-warning.active:hover,
3304 .open > .dropdown-toggle.btn-warning:hover,
3305 .btn-warning:active:focus,
3306 .btn-warning.active:focus,
3307 .open > .dropdown-toggle.btn-warning:focus,
3308 .btn-warning:active.focus,
3309 .btn-warning.active.focus,
3310 .open > .dropdown-toggle.btn-warning.focus {
3311 color: #fff;
3312 background-color: #d58512;
3313 border-color: #985f0d;
3314 }
3315 .btn-warning:active,
3316 .btn-warning.active,
3317 .open > .dropdown-toggle.btn-warning {
3318 background-image: none;
3319 }
3320 .btn-warning.disabled:hover,
3321 .btn-warning[disabled]:hover,
3322 fieldset[disabled] .btn-warning:hover,
3323 .btn-warning.disabled:focus,
3324 .btn-warning[disabled]:focus,
3325 fieldset[disabled] .btn-warning:focus,
3326 .btn-warning.disabled.focus,
3327 .btn-warning[disabled].focus,
3328 fieldset[disabled] .btn-warning.focus {
3329 background-color: #f0ad4e;
3330 border-color: #eea236;
3331 }
3332 .btn-warning .badge {
3333 color: #f0ad4e;
3334 background-color: #fff;
3335 }
3336 .btn-danger {
3337 color: #fff;
3338 background-color: #d9534f;
3339 border-color: #d43f3a;
3340 }
3341 .btn-danger:focus,
3342 .btn-danger.focus {
3343 color: #fff;
3344 background-color: #c9302c;
3345 border-color: #761c19;
3346 }
3347 .btn-danger:hover {
3348 color: #fff;
3349 background-color: #c9302c;
3350 border-color: #ac2925;
3351 }
3352 .btn-danger:active,
3353 .btn-danger.active,
3354 .open > .dropdown-toggle.btn-danger {
3355 color: #fff;
3356 background-color: #c9302c;
3357 border-color: #ac2925;
3358 }
3359 .btn-danger:active:hover,
3360 .btn-danger.active:hover,
3361 .open > .dropdown-toggle.btn-danger:hover,
3362 .btn-danger:active:focus,
3363 .btn-danger.active:focus,
3364 .open > .dropdown-toggle.btn-danger:focus,
3365 .btn-danger:active.focus,
3366 .btn-danger.active.focus,
3367 .open > .dropdown-toggle.btn-danger.focus {
3368 color: #fff;
3369 background-color: #ac2925;
3370 border-color: #761c19;
3371 }
3372 .btn-danger:active,
3373 .btn-danger.active,
3374 .open > .dropdown-toggle.btn-danger {
3375 background-image: none;
3376 }
3377 .btn-danger.disabled:hover,
3378 .btn-danger[disabled]:hover,
3379 fieldset[disabled] .btn-danger:hover,
3380 .btn-danger.disabled:focus,
3381 .btn-danger[disabled]:focus,
3382 fieldset[disabled] .btn-danger:focus,
3383 .btn-danger.disabled.focus,
3384 .btn-danger[disabled].focus,
3385 fieldset[disabled] .btn-danger.focus {
3386 background-color: #d9534f;
3387 border-color: #d43f3a;
3388 }
3389 .btn-danger .badge {
3390 color: #d9534f;
3391 background-color: #fff;
3392 }
3393 .btn-link {
3394 color: #337ab7;
3395 font-weight: normal;
3396 border-radius: 0;
3397 }
3398 .btn-link,
3399 .btn-link:active,
3400 .btn-link.active,
3401 .btn-link[disabled],
3402 fieldset[disabled] .btn-link {
3403 background-color: transparent;
3404 -webkit-box-shadow: none;
3405 box-shadow: none;
3406 }
3407 .btn-link,
3408 .btn-link:hover,
3409 .btn-link:focus,
3410 .btn-link:active {
3411 border-color: transparent;
3412 }
3413 .btn-link:hover,
3414 .btn-link:focus {
3415 color: #23527c;
3416 text-decoration: underline;
3417 background-color: transparent;
3418 }
3419 .btn-link[disabled]:hover,
3420 fieldset[disabled] .btn-link:hover,
3421 .btn-link[disabled]:focus,
3422 fieldset[disabled] .btn-link:focus {
3423 color: #777777;
3424 text-decoration: none;
3425 }
3426 .btn-lg,
3427 .btn-group-lg > .btn {
3428 padding: 10px 16px;
3429 font-size: 17px;
3430 line-height: 1.3333333;
3431 border-radius: 3px;
3432 }
3433 .btn-sm,
3434 .btn-group-sm > .btn {
3435 padding: 5px 10px;
3436 font-size: 12px;
3437 line-height: 1.5;
3438 border-radius: 1px;
3439 }
3440 .btn-xs,
3441 .btn-group-xs > .btn {
3442 padding: 1px 5px;
3443 font-size: 12px;
3444 line-height: 1.5;
3445 border-radius: 1px;
3446 }
3447 .btn-block {
3448 display: block;
3449 width: 100%;
3450 }
3451 .btn-block + .btn-block {
3452 margin-top: 5px;
3453 }
3454 input[type="submit"].btn-block,
3455 input[type="reset"].btn-block,
3456 input[type="button"].btn-block {
3457 width: 100%;
3458 }
3459 .fade {
3460 opacity: 0;
3461 -webkit-transition: opacity 0.15s linear;
3462 -o-transition: opacity 0.15s linear;
3463 transition: opacity 0.15s linear;
3464 }
3465 .fade.in {
3466 opacity: 1;
3467 }
3468 .collapse {
3469 display: none;
3470 }
3471 .collapse.in {
3472 display: block;
3473 }
3474 tr.collapse.in {
3475 display: table-row;
3476 }
3477 tbody.collapse.in {
3478 display: table-row-group;
3479 }
3480 .collapsing {
3481 position: relative;
3482 height: 0;
3483 overflow: hidden;
3484 -webkit-transition-property: height, visibility;
3485 transition-property: height, visibility;
3486 -webkit-transition-duration: 0.35s;
3487 transition-duration: 0.35s;
3488 -webkit-transition-timing-function: ease;
3489 transition-timing-function: ease;
3490 }
3491 .caret {
3492 display: inline-block;
3493 width: 0;
3494 height: 0;
3495 margin-left: 2px;
3496 vertical-align: middle;
3497 border-top: 4px dashed;
3498 border-top: 4px solid \9;
3499 border-right: 4px solid transparent;
3500 border-left: 4px solid transparent;
3501 }
3502 .dropup,
3503 .dropdown {
3504 position: relative;
3505 }
3506 .dropdown-toggle:focus {
3507 outline: 0;
3508 }
3509 .dropdown-menu {
3510 position: absolute;
3511 top: 100%;
3512 left: 0;
3513 z-index: 1000;
3514 display: none;
3515 float: left;
3516 min-width: 160px;
3517 padding: 5px 0;
3518 margin: 2px 0 0;
3519 list-style: none;
3520 font-size: 13px;
3521 text-align: left;
3522 background-color: #fff;
3523 border: 1px solid #ccc;
3524 border: 1px solid rgba(0, 0, 0, 0.15);
3525 border-radius: 2px;
3526 -webkit-box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);
3527 box-shadow: 0 6px 12px rgba(0, 0, 0, 0.175);
3528 background-clip: padding-box;
3529 }
3530 .dropdown-menu.pull-right {
3531 right: 0;
3532 left: auto;
3533 }
3534 .dropdown-menu .divider {
3535 height: 1px;
3536 margin: 8px 0;
3537 overflow: hidden;
3538 background-color: #e5e5e5;
3539 }
3540 .dropdown-menu > li > a {
3541 display: block;
3542 padding: 3px 20px;
3543 clear: both;
3544 font-weight: normal;
3545 line-height: 1.42857143;
3546 color: #333333;
3547 white-space: nowrap;
3548 }
3549 .dropdown-menu > li > a:hover,
3550 .dropdown-menu > li > a:focus {
3551 text-decoration: none;
3552 color: #262626;
3553 background-color: #f5f5f5;
3554 }
3555 .dropdown-menu > .active > a,
3556 .dropdown-menu > .active > a:hover,
3557 .dropdown-menu > .active > a:focus {
3558 color: #fff;
3559 text-decoration: none;
3560 outline: 0;
3561 background-color: #337ab7;
3562 }
3563 .dropdown-menu > .disabled > a,
3564 .dropdown-menu > .disabled > a:hover,
3565 .dropdown-menu > .disabled > a:focus {
3566 color: #777777;
3567 }
3568 .dropdown-menu > .disabled > a:hover,
3569 .dropdown-menu > .disabled > a:focus {
3570 text-decoration: none;
3571 background-color: transparent;
3572 background-image: none;
3573 filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
3574 cursor: not-allowed;
3575 }
3576 .open > .dropdown-menu {
3577 display: block;
3578 }
3579 .open > a {
3580 outline: 0;
3581 }
3582 .dropdown-menu-right {
3583 left: auto;
3584 right: 0;
3585 }
3586 .dropdown-menu-left {
3587 left: 0;
3588 right: auto;
3589 }
3590 .dropdown-header {
3591 display: block;
3592 padding: 3px 20px;
3593 font-size: 12px;
3594 line-height: 1.42857143;
3595 color: #777777;
3596 white-space: nowrap;
3597 }
3598 .dropdown-backdrop {
3599 position: fixed;
3600 left: 0;
3601 right: 0;
3602 bottom: 0;
3603 top: 0;
3604 z-index: 990;
3605 }
3606 .pull-right > .dropdown-menu {
3607 right: 0;
3608 left: auto;
3609 }
3610 .dropup .caret,
3611 .navbar-fixed-bottom .dropdown .caret {
3612 border-top: 0;
3613 border-bottom: 4px dashed;
3614 border-bottom: 4px solid \9;
3615 content: "";
3616 }
3617 .dropup .dropdown-menu,
3618 .navbar-fixed-bottom .dropdown .dropdown-menu {
3619 top: auto;
3620 bottom: 100%;
3621 margin-bottom: 2px;
3622 }
3623 @media (min-width: 541px) {
3624 .navbar-right .dropdown-menu {
3625 left: auto;
3626 right: 0;
3627 }
3628 .navbar-right .dropdown-menu-left {
3629 left: 0;
3630 right: auto;
3631 }
3632 }
3633 .btn-group,
3634 .btn-group-vertical {
3635 position: relative;
3636 display: inline-block;
3637 vertical-align: middle;
3638 }
3639 .btn-group > .btn,
3640 .btn-group-vertical > .btn {
3641 position: relative;
3642 float: left;
3643 }
3644 .btn-group > .btn:hover,
3645 .btn-group-vertical > .btn:hover,
3646 .btn-group > .btn:focus,
3647 .btn-group-vertical > .btn:focus,
3648 .btn-group > .btn:active,
3649 .btn-group-vertical > .btn:active,
3650 .btn-group > .btn.active,
3651 .btn-group-vertical > .btn.active {
3652 z-index: 2;
3653 }
3654 .btn-group .btn + .btn,
3655 .btn-group .btn + .btn-group,
3656 .btn-group .btn-group + .btn,
3657 .btn-group .btn-group + .btn-group {
3658 margin-left: -1px;
3659 }
3660 .btn-toolbar {
3661 margin-left: -5px;
3662 }
3663 .btn-toolbar .btn,
3664 .btn-toolbar .btn-group,
3665 .btn-toolbar .input-group {
3666 float: left;
3667 }
3668 .btn-toolbar > .btn,
3669 .btn-toolbar > .btn-group,
3670 .btn-toolbar > .input-group {
3671 margin-left: 5px;
3672 }
3673 .btn-group > .btn:not(:first-child):not(:last-child):not(.dropdown-toggle) {
3674 border-radius: 0;
3675 }
3676 .btn-group > .btn:first-child {
3677 margin-left: 0;
3678 }
3679 .btn-group > .btn:first-child:not(:last-child):not(.dropdown-toggle) {
3680 border-bottom-right-radius: 0;
3681 border-top-right-radius: 0;
3682 }
3683 .btn-group > .btn:last-child:not(:first-child),
3684 .btn-group > .dropdown-toggle:not(:first-child) {
3685 border-bottom-left-radius: 0;
3686 border-top-left-radius: 0;
3687 }
3688 .btn-group > .btn-group {
3689 float: left;
3690 }
3691 .btn-group > .btn-group:not(:first-child):not(:last-child) > .btn {
3692 border-radius: 0;
3693 }
3694 .btn-group > .btn-group:first-child:not(:last-child) > .btn:last-child,
3695 .btn-group > .btn-group:first-child:not(:last-child) > .dropdown-toggle {
3696 border-bottom-right-radius: 0;
3697 border-top-right-radius: 0;
3698 }
3699 .btn-group > .btn-group:last-child:not(:first-child) > .btn:first-child {
3700 border-bottom-left-radius: 0;
3701 border-top-left-radius: 0;
3702 }
3703 .btn-group .dropdown-toggle:active,
3704 .btn-group.open .dropdown-toggle {
3705 outline: 0;
3706 }
3707 .btn-group > .btn + .dropdown-toggle {
3708 padding-left: 8px;
3709 padding-right: 8px;
3710 }
3711 .btn-group > .btn-lg + .dropdown-toggle {
3712 padding-left: 12px;
3713 padding-right: 12px;
3714 }
3715 .btn-group.open .dropdown-toggle {
3716 -webkit-box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
3717 box-shadow: inset 0 3px 5px rgba(0, 0, 0, 0.125);
3718 }
3719 .btn-group.open .dropdown-toggle.btn-link {
3720 -webkit-box-shadow: none;
3721 box-shadow: none;
3722 }
3723 .btn .caret {
3724 margin-left: 0;
3725 }
3726 .btn-lg .caret {
3727 border-width: 5px 5px 0;
3728 border-bottom-width: 0;
3729 }
3730 .dropup .btn-lg .caret {
3731 border-width: 0 5px 5px;
3732 }
3733 .btn-group-vertical > .btn,
3734 .btn-group-vertical > .btn-group,
3735 .btn-group-vertical > .btn-group > .btn {
3736 display: block;
3737 float: none;
3738 width: 100%;
3739 max-width: 100%;
3740 }
3741 .btn-group-vertical > .btn-group > .btn {
3742 float: none;
3743 }
3744 .btn-group-vertical > .btn + .btn,
3745 .btn-group-vertical > .btn + .btn-group,
3746 .btn-group-vertical > .btn-group + .btn,
3747 .btn-group-vertical > .btn-group + .btn-group {
3748 margin-top: -1px;
3749 margin-left: 0;
3750 }
3751 .btn-group-vertical > .btn:not(:first-child):not(:last-child) {
3752 border-radius: 0;
3753 }
3754 .btn-group-vertical > .btn:first-child:not(:last-child) {
3755 border-top-right-radius: 2px;
3756 border-top-left-radius: 2px;
3757 border-bottom-right-radius: 0;
3758 border-bottom-left-radius: 0;
3759 }
3760 .btn-group-vertical > .btn:last-child:not(:first-child) {
3761 border-top-right-radius: 0;
3762 border-top-left-radius: 0;
3763 border-bottom-right-radius: 2px;
3764 border-bottom-left-radius: 2px;
3765 }
3766 .btn-group-vertical > .btn-group:not(:first-child):not(:last-child) > .btn {
3767 border-radius: 0;
3768 }
3769 .btn-group-vertical > .btn-group:first-child:not(:last-child) > .btn:last-child,
3770 .btn-group-vertical > .btn-group:first-child:not(:last-child) > .dropdown-toggle {
3771 border-bottom-right-radius: 0;
3772 border-bottom-left-radius: 0;
3773 }
3774 .btn-group-vertical > .btn-group:last-child:not(:first-child) > .btn:first-child {
3775 border-top-right-radius: 0;
3776 border-top-left-radius: 0;
3777 }
3778 .btn-group-justified {
3779 display: table;
3780 width: 100%;
3781 table-layout: fixed;
3782 border-collapse: separate;
3783 }
3784 .btn-group-justified > .btn,
3785 .btn-group-justified > .btn-group {
3786 float: none;
3787 display: table-cell;
3788 width: 1%;
3789 }
3790 .btn-group-justified > .btn-group .btn {
3791 width: 100%;
3792 }
3793 .btn-group-justified > .btn-group .dropdown-menu {
3794 left: auto;
3795 }
3796 [data-toggle="buttons"] > .btn input[type="radio"],
3797 [data-toggle="buttons"] > .btn-group > .btn input[type="radio"],
3798 [data-toggle="buttons"] > .btn input[type="checkbox"],
3799 [data-toggle="buttons"] > .btn-group > .btn input[type="checkbox"] {
3800 position: absolute;
3801 clip: rect(0, 0, 0, 0);
3802 pointer-events: none;
3803 }
3804 .input-group {
3805 position: relative;
3806 display: table;
3807 border-collapse: separate;
3808 }
3809 .input-group[class*="col-"] {
3810 float: none;
3811 padding-left: 0;
3812 padding-right: 0;
3813 }
3814 .input-group .form-control {
3815 position: relative;
3816 z-index: 2;
3817 float: left;
3818 width: 100%;
3819 margin-bottom: 0;
3820 }
3821 .input-group .form-control:focus {
3822 z-index: 3;
3823 }
3824 .input-group-lg > .form-control,
3825 .input-group-lg > .input-group-addon,
3826 .input-group-lg > .input-group-btn > .btn {
3827 height: 45px;
3828 padding: 10px 16px;
3829 font-size: 17px;
3830 line-height: 1.3333333;
3831 border-radius: 3px;
3832 }
3833 select.input-group-lg > .form-control,
3834 select.input-group-lg > .input-group-addon,
3835 select.input-group-lg > .input-group-btn > .btn {
3836 height: 45px;
3837 line-height: 45px;
3838 }
3839 textarea.input-group-lg > .form-control,
3840 textarea.input-group-lg > .input-group-addon,
3841 textarea.input-group-lg > .input-group-btn > .btn,
3842 select[multiple].input-group-lg > .form-control,
3843 select[multiple].input-group-lg > .input-group-addon,
3844 select[multiple].input-group-lg > .input-group-btn > .btn {
3845 height: auto;
3846 }
3847 .input-group-sm > .form-control,
3848 .input-group-sm > .input-group-addon,
3849 .input-group-sm > .input-group-btn > .btn {
3850 height: 30px;
3851 padding: 5px 10px;
3852 font-size: 12px;
3853 line-height: 1.5;
3854 border-radius: 1px;
3855 }
3856 select.input-group-sm > .form-control,
3857 select.input-group-sm > .input-group-addon,
3858 select.input-group-sm > .input-group-btn > .btn {
3859 height: 30px;
3860 line-height: 30px;
3861 }
3862 textarea.input-group-sm > .form-control,
3863 textarea.input-group-sm > .input-group-addon,
3864 textarea.input-group-sm > .input-group-btn > .btn,
3865 select[multiple].input-group-sm > .form-control,
3866 select[multiple].input-group-sm > .input-group-addon,
3867 select[multiple].input-group-sm > .input-group-btn > .btn {
3868 height: auto;
3869 }
3870 .input-group-addon,
3871 .input-group-btn,
3872 .input-group .form-control {
3873 display: table-cell;
3874 }
3875 .input-group-addon:not(:first-child):not(:last-child),
3876 .input-group-btn:not(:first-child):not(:last-child),
3877 .input-group .form-control:not(:first-child):not(:last-child) {
3878 border-radius: 0;
3879 }
3880 .input-group-addon,
3881 .input-group-btn {
3882 width: 1%;
3883 white-space: nowrap;
3884 vertical-align: middle;
3885 }
3886 .input-group-addon {
3887 padding: 6px 12px;
3888 font-size: 13px;
3889 font-weight: normal;
3890 line-height: 1;
3891 color: #555555;
3892 text-align: center;
3893 background-color: #eeeeee;
3894 border: 1px solid #ccc;
3895 border-radius: 2px;
3896 }
3897 .input-group-addon.input-sm {
3898 padding: 5px 10px;
3899 font-size: 12px;
3900 border-radius: 1px;
3901 }
3902 .input-group-addon.input-lg {
3903 padding: 10px 16px;
3904 font-size: 17px;
3905 border-radius: 3px;
3906 }
3907 .input-group-addon input[type="radio"],
3908 .input-group-addon input[type="checkbox"] {
3909 margin-top: 0;
3910 }
3911 .input-group .form-control:first-child,
3912 .input-group-addon:first-child,
3913 .input-group-btn:first-child > .btn,
3914 .input-group-btn:first-child > .btn-group > .btn,
3915 .input-group-btn:first-child > .dropdown-toggle,
3916 .input-group-btn:last-child > .btn:not(:last-child):not(.dropdown-toggle),
3917 .input-group-btn:last-child > .btn-group:not(:last-child) > .btn {
3918 border-bottom-right-radius: 0;
3919 border-top-right-radius: 0;
3920 }
3921 .input-group-addon:first-child {
3922 border-right: 0;
3923 }
3924 .input-group .form-control:last-child,
3925 .input-group-addon:last-child,
3926 .input-group-btn:last-child > .btn,
3927 .input-group-btn:last-child > .btn-group > .btn,
3928 .input-group-btn:last-child > .dropdown-toggle,
3929 .input-group-btn:first-child > .btn:not(:first-child),
3930 .input-group-btn:first-child > .btn-group:not(:first-child) > .btn {
3931 border-bottom-left-radius: 0;
3932 border-top-left-radius: 0;
3933 }
3934 .input-group-addon:last-child {
3935 border-left: 0;
3936 }
3937 .input-group-btn {
3938 position: relative;
3939 font-size: 0;
3940 white-space: nowrap;
3941 }
3942 .input-group-btn > .btn {
3943 position: relative;
3944 }
3945 .input-group-btn > .btn + .btn {
3946 margin-left: -1px;
3947 }
3948 .input-group-btn > .btn:hover,
3949 .input-group-btn > .btn:focus,
3950 .input-group-btn > .btn:active {
3951 z-index: 2;
3952 }
3953 .input-group-btn:first-child > .btn,
3954 .input-group-btn:first-child > .btn-group {
3955 margin-right: -1px;
3956 }
3957 .input-group-btn:last-child > .btn,
3958 .input-group-btn:last-child > .btn-group {
3959 z-index: 2;
3960 margin-left: -1px;
3961 }
3962 .nav {
3963 margin-bottom: 0;
3964 padding-left: 0;
3965 list-style: none;
3966 }
3967 .nav > li {
3968 position: relative;
3969 display: block;
3970 }
3971 .nav > li > a {
3972 position: relative;
3973 display: block;
3974 padding: 10px 15px;
3975 }
3976 .nav > li > a:hover,
3977 .nav > li > a:focus {
3978 text-decoration: none;
3979 background-color: #eeeeee;
3980 }
3981 .nav > li.disabled > a {
3982 color: #777777;
3983 }
3984 .nav > li.disabled > a:hover,
3985 .nav > li.disabled > a:focus {
3986 color: #777777;
3987 text-decoration: none;
3988 background-color: transparent;
3989 cursor: not-allowed;
3990 }
3991 .nav .open > a,
3992 .nav .open > a:hover,
3993 .nav .open > a:focus {
3994 background-color: #eeeeee;
3995 border-color: #337ab7;
3996 }
3997 .nav .nav-divider {
3998 height: 1px;
3999 margin: 8px 0;
4000 overflow: hidden;
4001 background-color: #e5e5e5;
4002 }
4003 .nav > li > a > img {
4004 max-width: none;
4005 }
4006 .nav-tabs {
4007 border-bottom: 1px solid #ddd;
4008 }
4009 .nav-tabs > li {
4010 float: left;
4011 margin-bottom: -1px;
4012 }
4013 .nav-tabs > li > a {
4014 margin-right: 2px;
4015 line-height: 1.42857143;
4016 border: 1px solid transparent;
4017 border-radius: 2px 2px 0 0;
4018 }
4019 .nav-tabs > li > a:hover {
4020 border-color: #eeeeee #eeeeee #ddd;
4021 }
4022 .nav-tabs > li.active > a,
4023 .nav-tabs > li.active > a:hover,
4024 .nav-tabs > li.active > a:focus {
4025 color: #555555;
4026 background-color: #fff;
4027 border: 1px solid #ddd;
4028 border-bottom-color: transparent;
4029 cursor: default;
4030 }
4031 .nav-tabs.nav-justified {
4032 width: 100%;
4033 border-bottom: 0;
4034 }
4035 .nav-tabs.nav-justified > li {
4036 float: none;
4037 }
4038 .nav-tabs.nav-justified > li > a {
4039 text-align: center;
4040 margin-bottom: 5px;
4041 }
4042 .nav-tabs.nav-justified > .dropdown .dropdown-menu {
4043 top: auto;
4044 left: auto;
4045 }
4046 @media (min-width: 768px) {
4047 .nav-tabs.nav-justified > li {
4048 display: table-cell;
4049 width: 1%;
4050 }
4051 .nav-tabs.nav-justified > li > a {
4052 margin-bottom: 0;
4053 }
4054 }
4055 .nav-tabs.nav-justified > li > a {
4056 margin-right: 0;
4057 border-radius: 2px;
4058 }
4059 .nav-tabs.nav-justified > .active > a,
4060 .nav-tabs.nav-justified > .active > a:hover,
4061 .nav-tabs.nav-justified > .active > a:focus {
4062 border: 1px solid #ddd;
4063 }
4064 @media (min-width: 768px) {
4065 .nav-tabs.nav-justified > li > a {
4066 border-bottom: 1px solid #ddd;
4067 border-radius: 2px 2px 0 0;
4068 }
4069 .nav-tabs.nav-justified > .active > a,
4070 .nav-tabs.nav-justified > .active > a:hover,
4071 .nav-tabs.nav-justified > .active > a:focus {
4072 border-bottom-color: #fff;
4073 }
4074 }
4075 .nav-pills > li {
4076 float: left;
4077 }
4078 .nav-pills > li > a {
4079 border-radius: 2px;
4080 }
4081 .nav-pills > li + li {
4082 margin-left: 2px;
4083 }
4084 .nav-pills > li.active > a,
4085 .nav-pills > li.active > a:hover,
4086 .nav-pills > li.active > a:focus {
4087 color: #fff;
4088 background-color: #337ab7;
4089 }
4090 .nav-stacked > li {
4091 float: none;
4092 }
4093 .nav-stacked > li + li {
4094 margin-top: 2px;
4095 margin-left: 0;
4096 }
4097 .nav-justified {
4098 width: 100%;
4099 }
4100 .nav-justified > li {
4101 float: none;
4102 }
4103 .nav-justified > li > a {
4104 text-align: center;
4105 margin-bottom: 5px;
4106 }
4107 .nav-justified > .dropdown .dropdown-menu {
4108 top: auto;
4109 left: auto;
4110 }
4111 @media (min-width: 768px) {
4112 .nav-justified > li {
4113 display: table-cell;
4114 width: 1%;
4115 }
4116 .nav-justified > li > a {
4117 margin-bottom: 0;
4118 }
4119 }
4120 .nav-tabs-justified {
4121 border-bottom: 0;
4122 }
4123 .nav-tabs-justified > li > a {
4124 margin-right: 0;
4125 border-radius: 2px;
4126 }
4127 .nav-tabs-justified > .active > a,
4128 .nav-tabs-justified > .active > a:hover,
4129 .nav-tabs-justified > .active > a:focus {
4130 border: 1px solid #ddd;
4131 }
4132 @media (min-width: 768px) {
4133 .nav-tabs-justified > li > a {
4134 border-bottom: 1px solid #ddd;
4135 border-radius: 2px 2px 0 0;
4136 }
4137 .nav-tabs-justified > .active > a,
4138 .nav-tabs-justified > .active > a:hover,
4139 .nav-tabs-justified > .active > a:focus {
4140 border-bottom-color: #fff;
4141 }
4142 }
4143 .tab-content > .tab-pane {
4144 display: none;
4145 }
4146 .tab-content > .active {
4147 display: block;
4148 }
4149 .nav-tabs .dropdown-menu {
4150 margin-top: -1px;
4151 border-top-right-radius: 0;
4152 border-top-left-radius: 0;
4153 }
4154 .navbar {
4155 position: relative;
4156 min-height: 30px;
4157 margin-bottom: 18px;
4158 border: 1px solid transparent;
4159 }
4160 @media (min-width: 541px) {
4161 .navbar {
4162 border-radius: 2px;
4163 }
4164 }
4165 @media (min-width: 541px) {
4166 .navbar-header {
4167 float: left;
4168 }
4169 }
4170 .navbar-collapse {
4171 overflow-x: visible;
4172 padding-right: 0px;
4173 padding-left: 0px;
4174 border-top: 1px solid transparent;
4175 box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
4176 -webkit-overflow-scrolling: touch;
4177 }
4178 .navbar-collapse.in {
4179 overflow-y: auto;
4180 }
4181 @media (min-width: 541px) {
4182 .navbar-collapse {
4183 width: auto;
4184 border-top: 0;
4185 box-shadow: none;
4186 }
4187 .navbar-collapse.collapse {
4188 display: block !important;
4189 height: auto !important;
4190 padding-bottom: 0;
4191 overflow: visible !important;
4192 }
4193 .navbar-collapse.in {
4194 overflow-y: visible;
4195 }
4196 .navbar-fixed-top .navbar-collapse,
4197 .navbar-static-top .navbar-collapse,
4198 .navbar-fixed-bottom .navbar-collapse {
4199 padding-left: 0;
4200 padding-right: 0;
4201 }
4202 }
4203 .navbar-fixed-top .navbar-collapse,
4204 .navbar-fixed-bottom .navbar-collapse {
4205 max-height: 340px;
4206 }
4207 @media (max-device-width: 540px) and (orientation: landscape) {
4208 .navbar-fixed-top .navbar-collapse,
4209 .navbar-fixed-bottom .navbar-collapse {
4210 max-height: 200px;
4211 }
4212 }
4213 .container > .navbar-header,
4214 .container-fluid > .navbar-header,
4215 .container > .navbar-collapse,
4216 .container-fluid > .navbar-collapse {
4217 margin-right: 0px;
4218 margin-left: 0px;
4219 }
4220 @media (min-width: 541px) {
4221 .container > .navbar-header,
4222 .container-fluid > .navbar-header,
4223 .container > .navbar-collapse,
4224 .container-fluid > .navbar-collapse {
4225 margin-right: 0;
4226 margin-left: 0;
4227 }
4228 }
4229 .navbar-static-top {
4230 z-index: 1000;
4231 border-width: 0 0 1px;
4232 }
4233 @media (min-width: 541px) {
4234 .navbar-static-top {
4235 border-radius: 0;
4236 }
4237 }
4238 .navbar-fixed-top,
4239 .navbar-fixed-bottom {
4240 position: fixed;
4241 right: 0;
4242 left: 0;
4243 z-index: 1030;
4244 }
4245 @media (min-width: 541px) {
4246 .navbar-fixed-top,
4247 .navbar-fixed-bottom {
4248 border-radius: 0;
4249 }
4250 }
4251 .navbar-fixed-top {
4252 top: 0;
4253 border-width: 0 0 1px;
4254 }
4255 .navbar-fixed-bottom {
4256 bottom: 0;
4257 margin-bottom: 0;
4258 border-width: 1px 0 0;
4259 }
4260 .navbar-brand {
4261 float: left;
4262 padding: 6px 0px;
4263 font-size: 17px;
4264 line-height: 18px;
4265 height: 30px;
4266 }
4267 .navbar-brand:hover,
4268 .navbar-brand:focus {
4269 text-decoration: none;
4270 }
4271 .navbar-brand > img {
4272 display: block;
4273 }
4274 @media (min-width: 541px) {
4275 .navbar > .container .navbar-brand,
4276 .navbar > .container-fluid .navbar-brand {
4277 margin-left: 0px;
4278 }
4279 }
4280 .navbar-toggle {
4281 position: relative;
4282 float: right;
4283 margin-right: 0px;
4284 padding: 9px 10px;
4285 margin-top: -2px;
4286 margin-bottom: -2px;
4287 background-color: transparent;
4288 background-image: none;
4289 border: 1px solid transparent;
4290 border-radius: 2px;
4291 }
4292 .navbar-toggle:focus {
4293 outline: 0;
4294 }
4295 .navbar-toggle .icon-bar {
4296 display: block;
4297 width: 22px;
4298 height: 2px;
4299 border-radius: 1px;
4300 }
4301 .navbar-toggle .icon-bar + .icon-bar {
4302 margin-top: 4px;
4303 }
4304 @media (min-width: 541px) {
4305 .navbar-toggle {
4306 display: none;
4307 }
4308 }
4309 .navbar-nav {
4310 margin: 3px 0px;
4311 }
4312 .navbar-nav > li > a {
4313 padding-top: 10px;
4314 padding-bottom: 10px;
4315 line-height: 18px;
4316 }
4317 @media (max-width: 540px) {
4318 .navbar-nav .open .dropdown-menu {
4319 position: static;
4320 float: none;
4321 width: auto;
4322 margin-top: 0;
4323 background-color: transparent;
4324 border: 0;
4325 box-shadow: none;
4326 }
4327 .navbar-nav .open .dropdown-menu > li > a,
4328 .navbar-nav .open .dropdown-menu .dropdown-header {
4329 padding: 5px 15px 5px 25px;
4330 }
4331 .navbar-nav .open .dropdown-menu > li > a {
4332 line-height: 18px;
4333 }
4334 .navbar-nav .open .dropdown-menu > li > a:hover,
4335 .navbar-nav .open .dropdown-menu > li > a:focus {
4336 background-image: none;
4337 }
4338 }
4339 @media (min-width: 541px) {
4340 .navbar-nav {
4341 float: left;
4342 margin: 0;
4343 }
4344 .navbar-nav > li {
4345 float: left;
4346 }
4347 .navbar-nav > li > a {
4348 padding-top: 6px;
4349 padding-bottom: 6px;
4350 }
4351 }
4352 .navbar-form {
4353 margin-left: 0px;
4354 margin-right: 0px;
4355 padding: 10px 0px;
4356 border-top: 1px solid transparent;
4357 border-bottom: 1px solid transparent;
4358 -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);
4359 box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1), 0 1px 0 rgba(255, 255, 255, 0.1);
4360 margin-top: -1px;
4361 margin-bottom: -1px;
4362 }
4363 @media (min-width: 768px) {
4364 .navbar-form .form-group {
4365 display: inline-block;
4366 margin-bottom: 0;
4367 vertical-align: middle;
4368 }
4369 .navbar-form .form-control {
4370 display: inline-block;
4371 width: auto;
4372 vertical-align: middle;
4373 }
4374 .navbar-form .form-control-static {
4375 display: inline-block;
4376 }
4377 .navbar-form .input-group {
4378 display: inline-table;
4379 vertical-align: middle;
4380 }
4381 .navbar-form .input-group .input-group-addon,
4382 .navbar-form .input-group .input-group-btn,
4383 .navbar-form .input-group .form-control {
4384 width: auto;
4385 }
4386 .navbar-form .input-group > .form-control {
4387 width: 100%;
4388 }
4389 .navbar-form .control-label {
4390 margin-bottom: 0;
4391 vertical-align: middle;
4392 }
4393 .navbar-form .radio,
4394 .navbar-form .checkbox {
4395 display: inline-block;
4396 margin-top: 0;
4397 margin-bottom: 0;
4398 vertical-align: middle;
4399 }
4400 .navbar-form .radio label,
4401 .navbar-form .checkbox label {
4402 padding-left: 0;
4403 }
4404 .navbar-form .radio input[type="radio"],
4405 .navbar-form .checkbox input[type="checkbox"] {
4406 position: relative;
4407 margin-left: 0;
4408 }
4409 .navbar-form .has-feedback .form-control-feedback {
4410 top: 0;
4411 }
4412 }
4413 @media (max-width: 540px) {
4414 .navbar-form .form-group {
4415 margin-bottom: 5px;
4416 }
4417 .navbar-form .form-group:last-child {
4418 margin-bottom: 0;
4419 }
4420 }
4421 @media (min-width: 541px) {
4422 .navbar-form {
4423 width: auto;
4424 border: 0;
4425 margin-left: 0;
4426 margin-right: 0;
4427 padding-top: 0;
4428 padding-bottom: 0;
4429 -webkit-box-shadow: none;
4430 box-shadow: none;
4431 }
4432 }
4433 .navbar-nav > li > .dropdown-menu {
4434 margin-top: 0;
4435 border-top-right-radius: 0;
4436 border-top-left-radius: 0;
4437 }
4438 .navbar-fixed-bottom .navbar-nav > li > .dropdown-menu {
4439 margin-bottom: 0;
4440 border-top-right-radius: 2px;
4441 border-top-left-radius: 2px;
4442 border-bottom-right-radius: 0;
4443 border-bottom-left-radius: 0;
4444 }
4445 .navbar-btn {
4446 margin-top: -1px;
4447 margin-bottom: -1px;
4448 }
4449 .navbar-btn.btn-sm {
4450 margin-top: 0px;
4451 margin-bottom: 0px;
4452 }
4453 .navbar-btn.btn-xs {
4454 margin-top: 4px;
4455 margin-bottom: 4px;
4456 }
4457 .navbar-text {
4458 margin-top: 6px;
4459 margin-bottom: 6px;
4460 }
4461 @media (min-width: 541px) {
4462 .navbar-text {
4463 float: left;
4464 margin-left: 0px;
4465 margin-right: 0px;
4466 }
4467 }
4468 @media (min-width: 541px) {
4469 .navbar-left {
4470 float: left !important;
4471 float: left;
4472 }
4473 .navbar-right {
4474 float: right !important;
4475 float: right;
4476 margin-right: 0px;
4477 }
4478 .navbar-right ~ .navbar-right {
4479 margin-right: 0;
4480 }
4481 }
4482 .navbar-default {
4483 background-color: #f8f8f8;
4484 border-color: #e7e7e7;
4485 }
4486 .navbar-default .navbar-brand {
4487 color: #777;
4488 }
4489 .navbar-default .navbar-brand:hover,
4490 .navbar-default .navbar-brand:focus {
4491 color: #5e5e5e;
4492 background-color: transparent;
4493 }
4494 .navbar-default .navbar-text {
4495 color: #777;
4496 }
4497 .navbar-default .navbar-nav > li > a {
4498 color: #777;
4499 }
4500 .navbar-default .navbar-nav > li > a:hover,
4501 .navbar-default .navbar-nav > li > a:focus {
4502 color: #333;
4503 background-color: transparent;
4504 }
4505 .navbar-default .navbar-nav > .active > a,
4506 .navbar-default .navbar-nav > .active > a:hover,
4507 .navbar-default .navbar-nav > .active > a:focus {
4508 color: #555;
4509 background-color: #e7e7e7;
4510 }
4511 .navbar-default .navbar-nav > .disabled > a,
4512 .navbar-default .navbar-nav > .disabled > a:hover,
4513 .navbar-default .navbar-nav > .disabled > a:focus {
4514 color: #ccc;
4515 background-color: transparent;
4516 }
4517 .navbar-default .navbar-toggle {
4518 border-color: #ddd;
4519 }
4520 .navbar-default .navbar-toggle:hover,
4521 .navbar-default .navbar-toggle:focus {
4522 background-color: #ddd;
4523 }
4524 .navbar-default .navbar-toggle .icon-bar {
4525 background-color: #888;
4526 }
4527 .navbar-default .navbar-collapse,
4528 .navbar-default .navbar-form {
4529 border-color: #e7e7e7;
4530 }
4531 .navbar-default .navbar-nav > .open > a,
4532 .navbar-default .navbar-nav > .open > a:hover,
4533 .navbar-default .navbar-nav > .open > a:focus {
4534 background-color: #e7e7e7;
4535 color: #555;
4536 }
4537 @media (max-width: 540px) {
4538 .navbar-default .navbar-nav .open .dropdown-menu > li > a {
4539 color: #777;
4540 }
4541 .navbar-default .navbar-nav .open .dropdown-menu > li > a:hover,
4542 .navbar-default .navbar-nav .open .dropdown-menu > li > a:focus {
4543 color: #333;
4544 background-color: transparent;
4545 }
4546 .navbar-default .navbar-nav .open .dropdown-menu > .active > a,
4547 .navbar-default .navbar-nav .open .dropdown-menu > .active > a:hover,
4548 .navbar-default .navbar-nav .open .dropdown-menu > .active > a:focus {
4549 color: #555;
4550 background-color: #e7e7e7;
4551 }
4552 .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a,
4553 .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:hover,
4554 .navbar-default .navbar-nav .open .dropdown-menu > .disabled > a:focus {
4555 color: #ccc;
4556 background-color: transparent;
4557 }
4558 }
4559 .navbar-default .navbar-link {
4560 color: #777;
4561 }
4562 .navbar-default .navbar-link:hover {
4563 color: #333;
4564 }
4565 .navbar-default .btn-link {
4566 color: #777;
4567 }
4568 .navbar-default .btn-link:hover,
4569 .navbar-default .btn-link:focus {
4570 color: #333;
4571 }
4572 .navbar-default .btn-link[disabled]:hover,
4573 fieldset[disabled] .navbar-default .btn-link:hover,
4574 .navbar-default .btn-link[disabled]:focus,
4575 fieldset[disabled] .navbar-default .btn-link:focus {
4576 color: #ccc;
4577 }
4578 .navbar-inverse {
4579 background-color: #222;
4580 border-color: #080808;
4581 }
4582 .navbar-inverse .navbar-brand {
4583 color: #9d9d9d;
4584 }
4585 .navbar-inverse .navbar-brand:hover,
4586 .navbar-inverse .navbar-brand:focus {
4587 color: #fff;
4588 background-color: transparent;
4589 }
4590 .navbar-inverse .navbar-text {
4591 color: #9d9d9d;
4592 }
4593 .navbar-inverse .navbar-nav > li > a {
4594 color: #9d9d9d;
4595 }
4596 .navbar-inverse .navbar-nav > li > a:hover,
4597 .navbar-inverse .navbar-nav > li > a:focus {
4598 color: #fff;
4599 background-color: transparent;
4600 }
4601 .navbar-inverse .navbar-nav > .active > a,
4602 .navbar-inverse .navbar-nav > .active > a:hover,
4603 .navbar-inverse .navbar-nav > .active > a:focus {
4604 color: #fff;
4605 background-color: #080808;
4606 }
4607 .navbar-inverse .navbar-nav > .disabled > a,
4608 .navbar-inverse .navbar-nav > .disabled > a:hover,
4609 .navbar-inverse .navbar-nav > .disabled > a:focus {
4610 color: #444;
4611 background-color: transparent;
4612 }
4613 .navbar-inverse .navbar-toggle {
4614 border-color: #333;
4615 }
4616 .navbar-inverse .navbar-toggle:hover,
4617 .navbar-inverse .navbar-toggle:focus {
4618 background-color: #333;
4619 }
4620 .navbar-inverse .navbar-toggle .icon-bar {
4621 background-color: #fff;
4622 }
4623 .navbar-inverse .navbar-collapse,
4624 .navbar-inverse .navbar-form {
4625 border-color: #101010;
4626 }
4627 .navbar-inverse .navbar-nav > .open > a,
4628 .navbar-inverse .navbar-nav > .open > a:hover,
4629 .navbar-inverse .navbar-nav > .open > a:focus {
4630 background-color: #080808;
4631 color: #fff;
4632 }
4633 @media (max-width: 540px) {
4634 .navbar-inverse .navbar-nav .open .dropdown-menu > .dropdown-header {
4635 border-color: #080808;
4636 }
4637 .navbar-inverse .navbar-nav .open .dropdown-menu .divider {
4638 background-color: #080808;
4639 }
4640 .navbar-inverse .navbar-nav .open .dropdown-menu > li > a {
4641 color: #9d9d9d;
4642 }
4643 .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:hover,
4644 .navbar-inverse .navbar-nav .open .dropdown-menu > li > a:focus {
4645 color: #fff;
4646 background-color: transparent;
4647 }
4648 .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a,
4649 .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:hover,
4650 .navbar-inverse .navbar-nav .open .dropdown-menu > .active > a:focus {
4651 color: #fff;
4652 background-color: #080808;
4653 }
4654 .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a,
4655 .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:hover,
4656 .navbar-inverse .navbar-nav .open .dropdown-menu > .disabled > a:focus {
4657 color: #444;
4658 background-color: transparent;
4659 }
4660 }
4661 .navbar-inverse .navbar-link {
4662 color: #9d9d9d;
4663 }
4664 .navbar-inverse .navbar-link:hover {
4665 color: #fff;
4666 }
4667 .navbar-inverse .btn-link {
4668 color: #9d9d9d;
4669 }
4670 .navbar-inverse .btn-link:hover,
4671 .navbar-inverse .btn-link:focus {
4672 color: #fff;
4673 }
4674 .navbar-inverse .btn-link[disabled]:hover,
4675 fieldset[disabled] .navbar-inverse .btn-link:hover,
4676 .navbar-inverse .btn-link[disabled]:focus,
4677 fieldset[disabled] .navbar-inverse .btn-link:focus {
4678 color: #444;
4679 }
4680 .breadcrumb {
4681 padding: 8px 15px;
4682 margin-bottom: 18px;
4683 list-style: none;
4684 background-color: #f5f5f5;
4685 border-radius: 2px;
4686 }
4687 .breadcrumb > li {
4688 display: inline-block;
4689 }
4690 .breadcrumb > li + li:before {
4691 content: "/\00a0";
4692 padding: 0 5px;
4693 color: #5e5e5e;
4694 }
4695 .breadcrumb > .active {
4696 color: #777777;
4697 }
4698 .pagination {
4699 display: inline-block;
4700 padding-left: 0;
4701 margin: 18px 0;
4702 border-radius: 2px;
4703 }
4704 .pagination > li {
4705 display: inline;
4706 }
4707 .pagination > li > a,
4708 .pagination > li > span {
4709 position: relative;
4710 float: left;
4711 padding: 6px 12px;
4712 line-height: 1.42857143;
4713 text-decoration: none;
4714 color: #337ab7;
4715 background-color: #fff;
4716 border: 1px solid #ddd;
4717 margin-left: -1px;
4718 }
4719 .pagination > li:first-child > a,
4720 .pagination > li:first-child > span {
4721 margin-left: 0;
4722 border-bottom-left-radius: 2px;
4723 border-top-left-radius: 2px;
4724 }
4725 .pagination > li:last-child > a,
4726 .pagination > li:last-child > span {
4727 border-bottom-right-radius: 2px;
4728 border-top-right-radius: 2px;
4729 }
4730 .pagination > li > a:hover,
4731 .pagination > li > span:hover,
4732 .pagination > li > a:focus,
4733 .pagination > li > span:focus {
4734 z-index: 2;
4735 color: #23527c;
4736 background-color: #eeeeee;
4737 border-color: #ddd;
4738 }
4739 .pagination > .active > a,
4740 .pagination > .active > span,
4741 .pagination > .active > a:hover,
4742 .pagination > .active > span:hover,
4743 .pagination > .active > a:focus,
4744 .pagination > .active > span:focus {
4745 z-index: 3;
4746 color: #fff;
4747 background-color: #337ab7;
4748 border-color: #337ab7;
4749 cursor: default;
4750 }
4751 .pagination > .disabled > span,
4752 .pagination > .disabled > span:hover,
4753 .pagination > .disabled > span:focus,
4754 .pagination > .disabled > a,
4755 .pagination > .disabled > a:hover,
4756 .pagination > .disabled > a:focus {
4757 color: #777777;
4758 background-color: #fff;
4759 border-color: #ddd;
4760 cursor: not-allowed;
4761 }
4762 .pagination-lg > li > a,
4763 .pagination-lg > li > span {
4764 padding: 10px 16px;
4765 font-size: 17px;
4766 line-height: 1.3333333;
4767 }
4768 .pagination-lg > li:first-child > a,
4769 .pagination-lg > li:first-child > span {
4770 border-bottom-left-radius: 3px;
4771 border-top-left-radius: 3px;
4772 }
4773 .pagination-lg > li:last-child > a,
4774 .pagination-lg > li:last-child > span {
4775 border-bottom-right-radius: 3px;
4776 border-top-right-radius: 3px;
4777 }
4778 .pagination-sm > li > a,
4779 .pagination-sm > li > span {
4780 padding: 5px 10px;
4781 font-size: 12px;
4782 line-height: 1.5;
4783 }
4784 .pagination-sm > li:first-child > a,
4785 .pagination-sm > li:first-child > span {
4786 border-bottom-left-radius: 1px;
4787 border-top-left-radius: 1px;
4788 }
4789 .pagination-sm > li:last-child > a,
4790 .pagination-sm > li:last-child > span {
4791 border-bottom-right-radius: 1px;
4792 border-top-right-radius: 1px;
4793 }
4794 .pager {
4795 padding-left: 0;
4796 margin: 18px 0;
4797 list-style: none;
4798 text-align: center;
4799 }
4800 .pager li {
4801 display: inline;
4802 }
4803 .pager li > a,
4804 .pager li > span {
4805 display: inline-block;
4806 padding: 5px 14px;
4807 background-color: #fff;
4808 border: 1px solid #ddd;
4809 border-radius: 15px;
4810 }
4811 .pager li > a:hover,
4812 .pager li > a:focus {
4813 text-decoration: none;
4814 background-color: #eeeeee;
4815 }
4816 .pager .next > a,
4817 .pager .next > span {
4818 float: right;
4819 }
4820 .pager .previous > a,
4821 .pager .previous > span {
4822 float: left;
4823 }
4824 .pager .disabled > a,
4825 .pager .disabled > a:hover,
4826 .pager .disabled > a:focus,
4827 .pager .disabled > span {
4828 color: #777777;
4829 background-color: #fff;
4830 cursor: not-allowed;
4831 }
4832 .label {
4833 display: inline;
4834 padding: .2em .6em .3em;
4835 font-size: 75%;
4836 font-weight: bold;
4837 line-height: 1;
4838 color: #fff;
4839 text-align: center;
4840 white-space: nowrap;
4841 vertical-align: baseline;
4842 border-radius: .25em;
4843 }
4844 a.label:hover,
4845 a.label:focus {
4846 color: #fff;
4847 text-decoration: none;
4848 cursor: pointer;
4849 }
4850 .label:empty {
4851 display: none;
4852 }
4853 .btn .label {
4854 position: relative;
4855 top: -1px;
4856 }
4857 .label-default {
4858 background-color: #777777;
4859 }
4860 .label-default[href]:hover,
4861 .label-default[href]:focus {
4862 background-color: #5e5e5e;
4863 }
4864 .label-primary {
4865 background-color: #337ab7;
4866 }
4867 .label-primary[href]:hover,
4868 .label-primary[href]:focus {
4869 background-color: #286090;
4870 }
4871 .label-success {
4872 background-color: #5cb85c;
4873 }
4874 .label-success[href]:hover,
4875 .label-success[href]:focus {
4876 background-color: #449d44;
4877 }
4878 .label-info {
4879 background-color: #5bc0de;
4880 }
4881 .label-info[href]:hover,
4882 .label-info[href]:focus {
4883 background-color: #31b0d5;
4884 }
4885 .label-warning {
4886 background-color: #f0ad4e;
4887 }
4888 .label-warning[href]:hover,
4889 .label-warning[href]:focus {
4890 background-color: #ec971f;
4891 }
4892 .label-danger {
4893 background-color: #d9534f;
4894 }
4895 .label-danger[href]:hover,
4896 .label-danger[href]:focus {
4897 background-color: #c9302c;
4898 }
4899 .badge {
4900 display: inline-block;
4901 min-width: 10px;
4902 padding: 3px 7px;
4903 font-size: 12px;
4904 font-weight: bold;
4905 color: #fff;
4906 line-height: 1;
4907 vertical-align: middle;
4908 white-space: nowrap;
4909 text-align: center;
4910 background-color: #777777;
4911 border-radius: 10px;
4912 }
4913 .badge:empty {
4914 display: none;
4915 }
4916 .btn .badge {
4917 position: relative;
4918 top: -1px;
4919 }
4920 .btn-xs .badge,
4921 .btn-group-xs > .btn .badge {
4922 top: 0;
4923 padding: 1px 5px;
4924 }
4925 a.badge:hover,
4926 a.badge:focus {
4927 color: #fff;
4928 text-decoration: none;
4929 cursor: pointer;
4930 }
4931 .list-group-item.active > .badge,
4932 .nav-pills > .active > a > .badge {
4933 color: #337ab7;
4934 background-color: #fff;
4935 }
4936 .list-group-item > .badge {
4937 float: right;
4938 }
4939 .list-group-item > .badge + .badge {
4940 margin-right: 5px;
4941 }
4942 .nav-pills > li > a > .badge {
4943 margin-left: 3px;
4944 }
4945 .jumbotron {
4946 padding-top: 30px;
4947 padding-bottom: 30px;
4948 margin-bottom: 30px;
4949 color: inherit;
4950 background-color: #eeeeee;
4951 }
4952 .jumbotron h1,
4953 .jumbotron .h1 {
4954 color: inherit;
4955 }
4956 .jumbotron p {
4957 margin-bottom: 15px;
4958 font-size: 20px;
4959 font-weight: 200;
4960 }
4961 .jumbotron > hr {
4962 border-top-color: #d5d5d5;
4963 }
4964 .container .jumbotron,
4965 .container-fluid .jumbotron {
4966 border-radius: 3px;
4967 padding-left: 0px;
4968 padding-right: 0px;
4969 }
4970 .jumbotron .container {
4971 max-width: 100%;
4972 }
4973 @media screen and (min-width: 768px) {
4974 .jumbotron {
4975 padding-top: 48px;
4976 padding-bottom: 48px;
4977 }
4978 .container .jumbotron,
4979 .container-fluid .jumbotron {
4980 padding-left: 60px;
4981 padding-right: 60px;
4982 }
4983 .jumbotron h1,
4984 .jumbotron .h1 {
4985 font-size: 59px;
4986 }
4987 }
4988 .thumbnail {
4989 display: block;
4990 padding: 4px;
4991 margin-bottom: 18px;
4992 line-height: 1.42857143;
4993 background-color: #fff;
4994 border: 1px solid #ddd;
4995 border-radius: 2px;
4996 -webkit-transition: border 0.2s ease-in-out;
4997 -o-transition: border 0.2s ease-in-out;
4998 transition: border 0.2s ease-in-out;
4999 }
5000 .thumbnail > img,
5001 .thumbnail a > img {
5002 margin-left: auto;
5003 margin-right: auto;
5004 }
5005 a.thumbnail:hover,
5006 a.thumbnail:focus,
5007 a.thumbnail.active {
5008 border-color: #337ab7;
5009 }
5010 .thumbnail .caption {
5011 padding: 9px;
5012 color: #000;
5013 }
5014 .alert {
5015 padding: 15px;
5016 margin-bottom: 18px;
5017 border: 1px solid transparent;
5018 border-radius: 2px;
5019 }
5020 .alert h4 {
5021 margin-top: 0;
5022 color: inherit;
5023 }
5024 .alert .alert-link {
5025 font-weight: bold;
5026 }
5027 .alert > p,
5028 .alert > ul {
5029 margin-bottom: 0;
5030 }
5031 .alert > p + p {
5032 margin-top: 5px;
5033 }
5034 .alert-dismissable,
5035 .alert-dismissible {
5036 padding-right: 35px;
5037 }
5038 .alert-dismissable .close,
5039 .alert-dismissible .close {
5040 position: relative;
5041 top: -2px;
5042 right: -21px;
5043 color: inherit;
5044 }
5045 .alert-success {
5046 background-color: #dff0d8;
5047 border-color: #d6e9c6;
5048 color: #3c763d;
5049 }
5050 .alert-success hr {
5051 border-top-color: #c9e2b3;
5052 }
5053 .alert-success .alert-link {
5054 color: #2b542c;
5055 }
5056 .alert-info {
5057 background-color: #d9edf7;
5058 border-color: #bce8f1;
5059 color: #31708f;
5060 }
5061 .alert-info hr {
5062 border-top-color: #a6e1ec;
5063 }
5064 .alert-info .alert-link {
5065 color: #245269;
5066 }
5067 .alert-warning {
5068 background-color: #fcf8e3;
5069 border-color: #faebcc;
5070 color: #8a6d3b;
5071 }
5072 .alert-warning hr {
5073 border-top-color: #f7e1b5;
5074 }
5075 .alert-warning .alert-link {
5076 color: #66512c;
5077 }
5078 .alert-danger {
5079 background-color: #f2dede;
5080 border-color: #ebccd1;
5081 color: #a94442;
5082 }
5083 .alert-danger hr {
5084 border-top-color: #e4b9c0;
5085 }
5086 .alert-danger .alert-link {
5087 color: #843534;
5088 }
5089 @-webkit-keyframes progress-bar-stripes {
5090 from {
5091 background-position: 40px 0;
5092 }
5093 to {
5094 background-position: 0 0;
5095 }
5096 }
5097 @keyframes progress-bar-stripes {
5098 from {
5099 background-position: 40px 0;
5100 }
5101 to {
5102 background-position: 0 0;
5103 }
5104 }
5105 .progress {
5106 overflow: hidden;
5107 height: 18px;
5108 margin-bottom: 18px;
5109 background-color: #f5f5f5;
5110 border-radius: 2px;
5111 -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
5112 box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
5113 }
5114 .progress-bar {
5115 float: left;
5116 width: 0%;
5117 height: 100%;
5118 font-size: 12px;
5119 line-height: 18px;
5120 color: #fff;
5121 text-align: center;
5122 background-color: #337ab7;
5123 -webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
5124 box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
5125 -webkit-transition: width 0.6s ease;
5126 -o-transition: width 0.6s ease;
5127 transition: width 0.6s ease;
5128 }
5129 .progress-striped .progress-bar,
5130 .progress-bar-striped {
5131 background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5132 background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5133 background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5134 background-size: 40px 40px;
5135 }
5136 .progress.active .progress-bar,
5137 .progress-bar.active {
5138 -webkit-animation: progress-bar-stripes 2s linear infinite;
5139 -o-animation: progress-bar-stripes 2s linear infinite;
5140 animation: progress-bar-stripes 2s linear infinite;
5141 }
5142 .progress-bar-success {
5143 background-color: #5cb85c;
5144 }
5145 .progress-striped .progress-bar-success {
5146 background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5147 background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5148 background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5149 }
5150 .progress-bar-info {
5151 background-color: #5bc0de;
5152 }
5153 .progress-striped .progress-bar-info {
5154 background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5155 background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5156 background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5157 }
5158 .progress-bar-warning {
5159 background-color: #f0ad4e;
5160 }
5161 .progress-striped .progress-bar-warning {
5162 background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5163 background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5164 background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5165 }
5166 .progress-bar-danger {
5167 background-color: #d9534f;
5168 }
5169 .progress-striped .progress-bar-danger {
5170 background-image: -webkit-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5171 background-image: -o-linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5172 background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.15) 25%, transparent 25%, transparent 50%, rgba(255, 255, 255, 0.15) 50%, rgba(255, 255, 255, 0.15) 75%, transparent 75%, transparent);
5173 }
5174 .media {
5175 margin-top: 15px;
5176 }
5177 .media:first-child {
5178 margin-top: 0;
5179 }
5180 .media,
5181 .media-body {
5182 zoom: 1;
5183 overflow: hidden;
5184 }
5185 .media-body {
5186 width: 10000px;
5187 }
5188 .media-object {
5189 display: block;
5190 }
5191 .media-object.img-thumbnail {
5192 max-width: none;
5193 }
5194 .media-right,
5195 .media > .pull-right {
5196 padding-left: 10px;
5197 }
5198 .media-left,
5199 .media > .pull-left {
5200 padding-right: 10px;
5201 }
5202 .media-left,
5203 .media-right,
5204 .media-body {
5205 display: table-cell;
5206 vertical-align: top;
5207 }
5208 .media-middle {
5209 vertical-align: middle;
5210 }
5211 .media-bottom {
5212 vertical-align: bottom;
5213 }
5214 .media-heading {
5215 margin-top: 0;
5216 margin-bottom: 5px;
5217 }
5218 .media-list {
5219 padding-left: 0;
5220 list-style: none;
5221 }
5222 .list-group {
5223 margin-bottom: 20px;
5224 padding-left: 0;
5225 }
5226 .list-group-item {
5227 position: relative;
5228 display: block;
5229 padding: 10px 15px;
5230 margin-bottom: -1px;
5231 background-color: #fff;
5232 border: 1px solid #ddd;
5233 }
5234 .list-group-item:first-child {
5235 border-top-right-radius: 2px;
5236 border-top-left-radius: 2px;
5237 }
5238 .list-group-item:last-child {
5239 margin-bottom: 0;
5240 border-bottom-right-radius: 2px;
5241 border-bottom-left-radius: 2px;
5242 }
5243 a.list-group-item,
5244 button.list-group-item {
5245 color: #555;
5246 }
5247 a.list-group-item .list-group-item-heading,
5248 button.list-group-item .list-group-item-heading {
5249 color: #333;
5250 }
5251 a.list-group-item:hover,
5252 button.list-group-item:hover,
5253 a.list-group-item:focus,
5254 button.list-group-item:focus {
5255 text-decoration: none;
5256 color: #555;
5257 background-color: #f5f5f5;
5258 }
5259 button.list-group-item {
5260 width: 100%;
5261 text-align: left;
5262 }
5263 .list-group-item.disabled,
5264 .list-group-item.disabled:hover,
5265 .list-group-item.disabled:focus {
5266 background-color: #eeeeee;
5267 color: #777777;
5268 cursor: not-allowed;
5269 }
5270 .list-group-item.disabled .list-group-item-heading,
5271 .list-group-item.disabled:hover .list-group-item-heading,
5272 .list-group-item.disabled:focus .list-group-item-heading {
5273 color: inherit;
5274 }
5275 .list-group-item.disabled .list-group-item-text,
5276 .list-group-item.disabled:hover .list-group-item-text,
5277 .list-group-item.disabled:focus .list-group-item-text {
5278 color: #777777;
5279 }
5280 .list-group-item.active,
5281 .list-group-item.active:hover,
5282 .list-group-item.active:focus {
5283 z-index: 2;
5284 color: #fff;
5285 background-color: #337ab7;
5286 border-color: #337ab7;
5287 }
5288 .list-group-item.active .list-group-item-heading,
5289 .list-group-item.active:hover .list-group-item-heading,
5290 .list-group-item.active:focus .list-group-item-heading,
5291 .list-group-item.active .list-group-item-heading > small,
5292 .list-group-item.active:hover .list-group-item-heading > small,
5293 .list-group-item.active:focus .list-group-item-heading > small,
5294 .list-group-item.active .list-group-item-heading > .small,
5295 .list-group-item.active:hover .list-group-item-heading > .small,
5296 .list-group-item.active:focus .list-group-item-heading > .small {
5297 color: inherit;
5298 }
5299 .list-group-item.active .list-group-item-text,
5300 .list-group-item.active:hover .list-group-item-text,
5301 .list-group-item.active:focus .list-group-item-text {
5302 color: #c7ddef;
5303 }
5304 .list-group-item-success {
5305 color: #3c763d;
5306 background-color: #dff0d8;
5307 }
5308 a.list-group-item-success,
5309 button.list-group-item-success {
5310 color: #3c763d;
5311 }
5312 a.list-group-item-success .list-group-item-heading,
5313 button.list-group-item-success .list-group-item-heading {
5314 color: inherit;
5315 }
5316 a.list-group-item-success:hover,
5317 button.list-group-item-success:hover,
5318 a.list-group-item-success:focus,
5319 button.list-group-item-success:focus {
5320 color: #3c763d;
5321 background-color: #d0e9c6;
5322 }
5323 a.list-group-item-success.active,
5324 button.list-group-item-success.active,
5325 a.list-group-item-success.active:hover,
5326 button.list-group-item-success.active:hover,
5327 a.list-group-item-success.active:focus,
5328 button.list-group-item-success.active:focus {
5329 color: #fff;
5330 background-color: #3c763d;
5331 border-color: #3c763d;
5332 }
5333 .list-group-item-info {
5334 color: #31708f;
5335 background-color: #d9edf7;
5336 }
5337 a.list-group-item-info,
5338 button.list-group-item-info {
5339 color: #31708f;
5340 }
5341 a.list-group-item-info .list-group-item-heading,
5342 button.list-group-item-info .list-group-item-heading {
5343 color: inherit;
5344 }
5345 a.list-group-item-info:hover,
5346 button.list-group-item-info:hover,
5347 a.list-group-item-info:focus,
5348 button.list-group-item-info:focus {
5349 color: #31708f;
5350 background-color: #c4e3f3;
5351 }
5352 a.list-group-item-info.active,
5353 button.list-group-item-info.active,
5354 a.list-group-item-info.active:hover,
5355 button.list-group-item-info.active:hover,
5356 a.list-group-item-info.active:focus,
5357 button.list-group-item-info.active:focus {
5358 color: #fff;
5359 background-color: #31708f;
5360 border-color: #31708f;
5361 }
5362 .list-group-item-warning {
5363 color: #8a6d3b;
5364 background-color: #fcf8e3;
5365 }
5366 a.list-group-item-warning,
5367 button.list-group-item-warning {
5368 color: #8a6d3b;
5369 }
5370 a.list-group-item-warning .list-group-item-heading,
5371 button.list-group-item-warning .list-group-item-heading {
5372 color: inherit;
5373 }
5374 a.list-group-item-warning:hover,
5375 button.list-group-item-warning:hover,
5376 a.list-group-item-warning:focus,
5377 button.list-group-item-warning:focus {
5378 color: #8a6d3b;
5379 background-color: #faf2cc;
5380 }
5381 a.list-group-item-warning.active,
5382 button.list-group-item-warning.active,
5383 a.list-group-item-warning.active:hover,
5384 button.list-group-item-warning.active:hover,
5385 a.list-group-item-warning.active:focus,
5386 button.list-group-item-warning.active:focus {
5387 color: #fff;
5388 background-color: #8a6d3b;
5389 border-color: #8a6d3b;
5390 }
5391 .list-group-item-danger {
5392 color: #a94442;
5393 background-color: #f2dede;
5394 }
5395 a.list-group-item-danger,
5396 button.list-group-item-danger {
5397 color: #a94442;
5398 }
5399 a.list-group-item-danger .list-group-item-heading,
5400 button.list-group-item-danger .list-group-item-heading {
5401 color: inherit;
5402 }
5403 a.list-group-item-danger:hover,
5404 button.list-group-item-danger:hover,
5405 a.list-group-item-danger:focus,
5406 button.list-group-item-danger:focus {
5407 color: #a94442;
5408 background-color: #ebcccc;
5409 }
5410 a.list-group-item-danger.active,
5411 button.list-group-item-danger.active,
5412 a.list-group-item-danger.active:hover,
5413 button.list-group-item-danger.active:hover,
5414 a.list-group-item-danger.active:focus,
5415 button.list-group-item-danger.active:focus {
5416 color: #fff;
5417 background-color: #a94442;
5418 border-color: #a94442;
5419 }
5420 .list-group-item-heading {
5421 margin-top: 0;
5422 margin-bottom: 5px;
5423 }
5424 .list-group-item-text {
5425 margin-bottom: 0;
5426 line-height: 1.3;
5427 }
5428 .panel {
5429 margin-bottom: 18px;
5430 background-color: #fff;
5431 border: 1px solid transparent;
5432 border-radius: 2px;
5433 -webkit-box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);
5434 box-shadow: 0 1px 1px rgba(0, 0, 0, 0.05);
5435 }
5436 .panel-body {
5437 padding: 15px;
5438 }
5439 .panel-heading {
5440 padding: 10px 15px;
5441 border-bottom: 1px solid transparent;
5442 border-top-right-radius: 1px;
5443 border-top-left-radius: 1px;
5444 }
5445 .panel-heading > .dropdown .dropdown-toggle {
5446 color: inherit;
5447 }
5448 .panel-title {
5449 margin-top: 0;
5450 margin-bottom: 0;
5451 font-size: 15px;
5452 color: inherit;
5453 }
5454 .panel-title > a,
5455 .panel-title > small,
5456 .panel-title > .small,
5457 .panel-title > small > a,
5458 .panel-title > .small > a {
5459 color: inherit;
5460 }
5461 .panel-footer {
5462 padding: 10px 15px;
5463 background-color: #f5f5f5;
5464 border-top: 1px solid #ddd;
5465 border-bottom-right-radius: 1px;
5466 border-bottom-left-radius: 1px;
5467 }
5468 .panel > .list-group,
5469 .panel > .panel-collapse > .list-group {
5470 margin-bottom: 0;
5471 }
5472 .panel > .list-group .list-group-item,
5473 .panel > .panel-collapse > .list-group .list-group-item {
5474 border-width: 1px 0;
5475 border-radius: 0;
5476 }
5477 .panel > .list-group:first-child .list-group-item:first-child,
5478 .panel > .panel-collapse > .list-group:first-child .list-group-item:first-child {
5479 border-top: 0;
5480 border-top-right-radius: 1px;
5481 border-top-left-radius: 1px;
5482 }
5483 .panel > .list-group:last-child .list-group-item:last-child,
5484 .panel > .panel-collapse > .list-group:last-child .list-group-item:last-child {
5485 border-bottom: 0;
5486 border-bottom-right-radius: 1px;
5487 border-bottom-left-radius: 1px;
5488 }
5489 .panel > .panel-heading + .panel-collapse > .list-group .list-group-item:first-child {
5490 border-top-right-radius: 0;
5491 border-top-left-radius: 0;
5492 }
5493 .panel-heading + .list-group .list-group-item:first-child {
5494 border-top-width: 0;
5495 }
5496 .list-group + .panel-footer {
5497 border-top-width: 0;
5498 }
5499 .panel > .table,
5500 .panel > .table-responsive > .table,
5501 .panel > .panel-collapse > .table {
5502 margin-bottom: 0;
5503 }
5504 .panel > .table caption,
5505 .panel > .table-responsive > .table caption,
5506 .panel > .panel-collapse > .table caption {
5507 padding-left: 15px;
5508 padding-right: 15px;
5509 }
5510 .panel > .table:first-child,
5511 .panel > .table-responsive:first-child > .table:first-child {
5512 border-top-right-radius: 1px;
5513 border-top-left-radius: 1px;
5514 }
5515 .panel > .table:first-child > thead:first-child > tr:first-child,
5516 .panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child,
5517 .panel > .table:first-child > tbody:first-child > tr:first-child,
5518 .panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child {
5519 border-top-left-radius: 1px;
5520 border-top-right-radius: 1px;
5521 }
5522 .panel > .table:first-child > thead:first-child > tr:first-child td:first-child,
5523 .panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:first-child,
5524 .panel > .table:first-child > tbody:first-child > tr:first-child td:first-child,
5525 .panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:first-child,
5526 .panel > .table:first-child > thead:first-child > tr:first-child th:first-child,
5527 .panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:first-child,
5528 .panel > .table:first-child > tbody:first-child > tr:first-child th:first-child,
5529 .panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:first-child {
5530 border-top-left-radius: 1px;
5531 }
5532 .panel > .table:first-child > thead:first-child > tr:first-child td:last-child,
5533 .panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child td:last-child,
5534 .panel > .table:first-child > tbody:first-child > tr:first-child td:last-child,
5535 .panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child td:last-child,
5536 .panel > .table:first-child > thead:first-child > tr:first-child th:last-child,
5537 .panel > .table-responsive:first-child > .table:first-child > thead:first-child > tr:first-child th:last-child,
5538 .panel > .table:first-child > tbody:first-child > tr:first-child th:last-child,
5539 .panel > .table-responsive:first-child > .table:first-child > tbody:first-child > tr:first-child th:last-child {
5540 border-top-right-radius: 1px;
5541 }
5542 .panel > .table:last-child,
5543 .panel > .table-responsive:last-child > .table:last-child {
5544 border-bottom-right-radius: 1px;
5545 border-bottom-left-radius: 1px;
5546 }
5547 .panel > .table:last-child > tbody:last-child > tr:last-child,
5548 .panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child,
5549 .panel > .table:last-child > tfoot:last-child > tr:last-child,
5550 .panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child {
5551 border-bottom-left-radius: 1px;
5552 border-bottom-right-radius: 1px;
5553 }
5554 .panel > .table:last-child > tbody:last-child > tr:last-child td:first-child,
5555 .panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:first-child,
5556 .panel > .table:last-child > tfoot:last-child > tr:last-child td:first-child,
5557 .panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:first-child,
5558 .panel > .table:last-child > tbody:last-child > tr:last-child th:first-child,
5559 .panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:first-child,
5560 .panel > .table:last-child > tfoot:last-child > tr:last-child th:first-child,
5561 .panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:first-child {
5562 border-bottom-left-radius: 1px;
5563 }
5564 .panel > .table:last-child > tbody:last-child > tr:last-child td:last-child,
5565 .panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child td:last-child,
5566 .panel > .table:last-child > tfoot:last-child > tr:last-child td:last-child,
5567 .panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child td:last-child,
5568 .panel > .table:last-child > tbody:last-child > tr:last-child th:last-child,
5569 .panel > .table-responsive:last-child > .table:last-child > tbody:last-child > tr:last-child th:last-child,
5570 .panel > .table:last-child > tfoot:last-child > tr:last-child th:last-child,
5571 .panel > .table-responsive:last-child > .table:last-child > tfoot:last-child > tr:last-child th:last-child {
5572 border-bottom-right-radius: 1px;
5573 }
5574 .panel > .panel-body + .table,
5575 .panel > .panel-body + .table-responsive,
5576 .panel > .table + .panel-body,
5577 .panel > .table-responsive + .panel-body {
5578 border-top: 1px solid #ddd;
5579 }
5580 .panel > .table > tbody:first-child > tr:first-child th,
5581 .panel > .table > tbody:first-child > tr:first-child td {
5582 border-top: 0;
5583 }
5584 .panel > .table-bordered,
5585 .panel > .table-responsive > .table-bordered {
5586 border: 0;
5587 }
5588 .panel > .table-bordered > thead > tr > th:first-child,
5589 .panel > .table-responsive > .table-bordered > thead > tr > th:first-child,
5590 .panel > .table-bordered > tbody > tr > th:first-child,
5591 .panel > .table-responsive > .table-bordered > tbody > tr > th:first-child,
5592 .panel > .table-bordered > tfoot > tr > th:first-child,
5593 .panel > .table-responsive > .table-bordered > tfoot > tr > th:first-child,
5594 .panel > .table-bordered > thead > tr > td:first-child,
5595 .panel > .table-responsive > .table-bordered > thead > tr > td:first-child,
5596 .panel > .table-bordered > tbody > tr > td:first-child,
5597 .panel > .table-responsive > .table-bordered > tbody > tr > td:first-child,
5598 .panel > .table-bordered > tfoot > tr > td:first-child,
5599 .panel > .table-responsive > .table-bordered > tfoot > tr > td:first-child {
5600 border-left: 0;
5601 }
5602 .panel > .table-bordered > thead > tr > th:last-child,
5603 .panel > .table-responsive > .table-bordered > thead > tr > th:last-child,
5604 .panel > .table-bordered > tbody > tr > th:last-child,
5605 .panel > .table-responsive > .table-bordered > tbody > tr > th:last-child,
5606 .panel > .table-bordered > tfoot > tr > th:last-child,
5607 .panel > .table-responsive > .table-bordered > tfoot > tr > th:last-child,
5608 .panel > .table-bordered > thead > tr > td:last-child,
5609 .panel > .table-responsive > .table-bordered > thead > tr > td:last-child,
5610 .panel > .table-bordered > tbody > tr > td:last-child,
5611 .panel > .table-responsive > .table-bordered > tbody > tr > td:last-child,
5612 .panel > .table-bordered > tfoot > tr > td:last-child,
5613 .panel > .table-responsive > .table-bordered > tfoot > tr > td:last-child {
5614 border-right: 0;
5615 }
5616 .panel > .table-bordered > thead > tr:first-child > td,
5617 .panel > .table-responsive > .table-bordered > thead > tr:first-child > td,
5618 .panel > .table-bordered > tbody > tr:first-child > td,
5619 .panel > .table-responsive > .table-bordered > tbody > tr:first-child > td,
5620 .panel > .table-bordered > thead > tr:first-child > th,
5621 .panel > .table-responsive > .table-bordered > thead > tr:first-child > th,
5622 .panel > .table-bordered > tbody > tr:first-child > th,
5623 .panel > .table-responsive > .table-bordered > tbody > tr:first-child > th {
5624 border-bottom: 0;
5625 }
5626 .panel > .table-bordered > tbody > tr:last-child > td,
5627 .panel > .table-responsive > .table-bordered > tbody > tr:last-child > td,
5628 .panel > .table-bordered > tfoot > tr:last-child > td,
5629 .panel > .table-responsive > .table-bordered > tfoot > tr:last-child > td,
5630 .panel > .table-bordered > tbody > tr:last-child > th,
5631 .panel > .table-responsive > .table-bordered > tbody > tr:last-child > th,
5632 .panel > .table-bordered > tfoot > tr:last-child > th,
5633 .panel > .table-responsive > .table-bordered > tfoot > tr:last-child > th {
5634 border-bottom: 0;
5635 }
5636 .panel > .table-responsive {
5637 border: 0;
5638 margin-bottom: 0;
5639 }
5640 .panel-group {
5641 margin-bottom: 18px;
5642 }
5643 .panel-group .panel {
5644 margin-bottom: 0;
5645 border-radius: 2px;
5646 }
5647 .panel-group .panel + .panel {
5648 margin-top: 5px;
5649 }
5650 .panel-group .panel-heading {
5651 border-bottom: 0;
5652 }
5653 .panel-group .panel-heading + .panel-collapse > .panel-body,
5654 .panel-group .panel-heading + .panel-collapse > .list-group {
5655 border-top: 1px solid #ddd;
5656 }
5657 .panel-group .panel-footer {
5658 border-top: 0;
5659 }
5660 .panel-group .panel-footer + .panel-collapse .panel-body {
5661 border-bottom: 1px solid #ddd;
5662 }
5663 .panel-default {
5664 border-color: #ddd;
5665 }
5666 .panel-default > .panel-heading {
5667 color: #333333;
5668 background-color: #f5f5f5;
5669 border-color: #ddd;
5670 }
5671 .panel-default > .panel-heading + .panel-collapse > .panel-body {
5672 border-top-color: #ddd;
5673 }
5674 .panel-default > .panel-heading .badge {
5675 color: #f5f5f5;
5676 background-color: #333333;
5677 }
5678 .panel-default > .panel-footer + .panel-collapse > .panel-body {
5679 border-bottom-color: #ddd;
5680 }
5681 .panel-primary {
5682 border-color: #337ab7;
5683 }
5684 .panel-primary > .panel-heading {
5685 color: #fff;
5686 background-color: #337ab7;
5687 border-color: #337ab7;
5688 }
5689 .panel-primary > .panel-heading + .panel-collapse > .panel-body {
5690 border-top-color: #337ab7;
5691 }
5692 .panel-primary > .panel-heading .badge {
5693 color: #337ab7;
5694 background-color: #fff;
5695 }
5696 .panel-primary > .panel-footer + .panel-collapse > .panel-body {
5697 border-bottom-color: #337ab7;
5698 }
5699 .panel-success {
5700 border-color: #d6e9c6;
5701 }
5702 .panel-success > .panel-heading {
5703 color: #3c763d;
5704 background-color: #dff0d8;
5705 border-color: #d6e9c6;
5706 }
5707 .panel-success > .panel-heading + .panel-collapse > .panel-body {
5708 border-top-color: #d6e9c6;
5709 }
5710 .panel-success > .panel-heading .badge {
5711 color: #dff0d8;
5712 background-color: #3c763d;
5713 }
5714 .panel-success > .panel-footer + .panel-collapse > .panel-body {
5715 border-bottom-color: #d6e9c6;
5716 }
5717 .panel-info {
5718 border-color: #bce8f1;
5719 }
5720 .panel-info > .panel-heading {
5721 color: #31708f;
5722 background-color: #d9edf7;
5723 border-color: #bce8f1;
5724 }
5725 .panel-info > .panel-heading + .panel-collapse > .panel-body {
5726 border-top-color: #bce8f1;
5727 }
5728 .panel-info > .panel-heading .badge {
5729 color: #d9edf7;
5730 background-color: #31708f;
5731 }
5732 .panel-info > .panel-footer + .panel-collapse > .panel-body {
5733 border-bottom-color: #bce8f1;
5734 }
5735 .panel-warning {
5736 border-color: #faebcc;
5737 }
5738 .panel-warning > .panel-heading {
5739 color: #8a6d3b;
5740 background-color: #fcf8e3;
5741 border-color: #faebcc;
5742 }
5743 .panel-warning > .panel-heading + .panel-collapse > .panel-body {
5744 border-top-color: #faebcc;
5745 }
5746 .panel-warning > .panel-heading .badge {
5747 color: #fcf8e3;
5748 background-color: #8a6d3b;
5749 }
5750 .panel-warning > .panel-footer + .panel-collapse > .panel-body {
5751 border-bottom-color: #faebcc;
5752 }
5753 .panel-danger {
5754 border-color: #ebccd1;
5755 }
5756 .panel-danger > .panel-heading {
5757 color: #a94442;
5758 background-color: #f2dede;
5759 border-color: #ebccd1;
5760 }
5761 .panel-danger > .panel-heading + .panel-collapse > .panel-body {
5762 border-top-color: #ebccd1;
5763 }
5764 .panel-danger > .panel-heading .badge {
5765 color: #f2dede;
5766 background-color: #a94442;
5767 }
5768 .panel-danger > .panel-footer + .panel-collapse > .panel-body {
5769 border-bottom-color: #ebccd1;
5770 }
5771 .embed-responsive {
5772 position: relative;
5773 display: block;
5774 height: 0;
5775 padding: 0;
5776 overflow: hidden;
5777 }
5778 .embed-responsive .embed-responsive-item,
5779 .embed-responsive iframe,
5780 .embed-responsive embed,
5781 .embed-responsive object,
5782 .embed-responsive video {
5783 position: absolute;
5784 top: 0;
5785 left: 0;
5786 bottom: 0;
5787 height: 100%;
5788 width: 100%;
5789 border: 0;
5790 }
5791 .embed-responsive-16by9 {
5792 padding-bottom: 56.25%;
5793 }
5794 .embed-responsive-4by3 {
5795 padding-bottom: 75%;
5796 }
5797 .well {
5798 min-height: 20px;
5799 padding: 19px;
5800 margin-bottom: 20px;
5801 background-color: #f5f5f5;
5802 border: 1px solid #e3e3e3;
5803 border-radius: 2px;
5804 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);
5805 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.05);
5806 }
5807 .well blockquote {
5808 border-color: #ddd;
5809 border-color: rgba(0, 0, 0, 0.15);
5810 }
5811 .well-lg {
5812 padding: 24px;
5813 border-radius: 3px;
5814 }
5815 .well-sm {
5816 padding: 9px;
5817 border-radius: 1px;
5818 }
5819 .close {
5820 float: right;
5821 font-size: 19.5px;
5822 font-weight: bold;
5823 line-height: 1;
5824 color: #000;
5825 text-shadow: 0 1px 0 #fff;
5826 opacity: 0.2;
5827 filter: alpha(opacity=20);
5828 }
5829 .close:hover,
5830 .close:focus {
5831 color: #000;
5832 text-decoration: none;
5833 cursor: pointer;
5834 opacity: 0.5;
5835 filter: alpha(opacity=50);
5836 }
5837 button.close {
5838 padding: 0;
5839 cursor: pointer;
5840 background: transparent;
5841 border: 0;
5842 -webkit-appearance: none;
5843 }
5844 .modal-open {
5845 overflow: hidden;
5846 }
5847 .modal {
5848 display: none;
5849 overflow: hidden;
5850 position: fixed;
5851 top: 0;
5852 right: 0;
5853 bottom: 0;
5854 left: 0;
5855 z-index: 1050;
5856 -webkit-overflow-scrolling: touch;
5857 outline: 0;
5858 }
5859 .modal.fade .modal-dialog {
5860 -webkit-transform: translate(0, -25%);
5861 -ms-transform: translate(0, -25%);
5862 -o-transform: translate(0, -25%);
5863 transform: translate(0, -25%);
5864 -webkit-transition: -webkit-transform 0.3s ease-out;
5865 -moz-transition: -moz-transform 0.3s ease-out;
5866 -o-transition: -o-transform 0.3s ease-out;
5867 transition: transform 0.3s ease-out;
5868 }
5869 .modal.in .modal-dialog {
5870 -webkit-transform: translate(0, 0);
5871 -ms-transform: translate(0, 0);
5872 -o-transform: translate(0, 0);
5873 transform: translate(0, 0);
5874 }
5875 .modal-open .modal {
5876 overflow-x: hidden;
5877 overflow-y: auto;
5878 }
5879 .modal-dialog {
5880 position: relative;
5881 width: auto;
5882 margin: 10px;
5883 }
5884 .modal-content {
5885 position: relative;
5886 background-color: #fff;
5887 border: 1px solid #999;
5888 border: 1px solid rgba(0, 0, 0, 0.2);
5889 border-radius: 3px;
5890 -webkit-box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);
5891 box-shadow: 0 3px 9px rgba(0, 0, 0, 0.5);
5892 background-clip: padding-box;
5893 outline: 0;
5894 }
5895 .modal-backdrop {
5896 position: fixed;
5897 top: 0;
5898 right: 0;
5899 bottom: 0;
5900 left: 0;
5901 z-index: 1040;
5902 background-color: #000;
5903 }
5904 .modal-backdrop.fade {
5905 opacity: 0;
5906 filter: alpha(opacity=0);
5907 }
5908 .modal-backdrop.in {
5909 opacity: 0.5;
5910 filter: alpha(opacity=50);
5911 }
5912 .modal-header {
5913 padding: 15px;
5914 border-bottom: 1px solid #e5e5e5;
5915 }
5916 .modal-header .close {
5917 margin-top: -2px;
5918 }
5919 .modal-title {
5920 margin: 0;
5921 line-height: 1.42857143;
5922 }
5923 .modal-body {
5924 position: relative;
5925 padding: 15px;
5926 }
5927 .modal-footer {
5928 padding: 15px;
5929 text-align: right;
5930 border-top: 1px solid #e5e5e5;
5931 }
5932 .modal-footer .btn + .btn {
5933 margin-left: 5px;
5934 margin-bottom: 0;
5935 }
5936 .modal-footer .btn-group .btn + .btn {
5937 margin-left: -1px;
5938 }
5939 .modal-footer .btn-block + .btn-block {
5940 margin-left: 0;
5941 }
5942 .modal-scrollbar-measure {
5943 position: absolute;
5944 top: -9999px;
5945 width: 50px;
5946 height: 50px;
5947 overflow: scroll;
5948 }
5949 @media (min-width: 768px) {
5950 .modal-dialog {
5951 width: 600px;
5952 margin: 30px auto;
5953 }
5954 .modal-content {
5955 -webkit-box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);
5956 box-shadow: 0 5px 15px rgba(0, 0, 0, 0.5);
5957 }
5958 .modal-sm {
5959 width: 300px;
5960 }
5961 }
5962 @media (min-width: 992px) {
5963 .modal-lg {
5964 width: 900px;
5965 }
5966 }
5967 .tooltip {
5968 position: absolute;
5969 z-index: 1070;
5970 display: block;
5971 font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
5972 font-style: normal;
5973 font-weight: normal;
5974 letter-spacing: normal;
5975 line-break: auto;
5976 line-height: 1.42857143;
5977 text-align: left;
5978 text-align: start;
5979 text-decoration: none;
5980 text-shadow: none;
5981 text-transform: none;
5982 white-space: normal;
5983 word-break: normal;
5984 word-spacing: normal;
5985 word-wrap: normal;
5986 font-size: 12px;
5987 opacity: 0;
5988 filter: alpha(opacity=0);
5989 }
5990 .tooltip.in {
5991 opacity: 0.9;
5992 filter: alpha(opacity=90);
5993 }
5994 .tooltip.top {
5995 margin-top: -3px;
5996 padding: 5px 0;
5997 }
5998 .tooltip.right {
5999 margin-left: 3px;
6000 padding: 0 5px;
6001 }
6002 .tooltip.bottom {
6003 margin-top: 3px;
6004 padding: 5px 0;
6005 }
6006 .tooltip.left {
6007 margin-left: -3px;
6008 padding: 0 5px;
6009 }
6010 .tooltip-inner {
6011 max-width: 200px;
6012 padding: 3px 8px;
6013 color: #fff;
6014 text-align: center;
6015 background-color: #000;
6016 border-radius: 2px;
6017 }
6018 .tooltip-arrow {
6019 position: absolute;
6020 width: 0;
6021 height: 0;
6022 border-color: transparent;
6023 border-style: solid;
6024 }
6025 .tooltip.top .tooltip-arrow {
6026 bottom: 0;
6027 left: 50%;
6028 margin-left: -5px;
6029 border-width: 5px 5px 0;
6030 border-top-color: #000;
6031 }
6032 .tooltip.top-left .tooltip-arrow {
6033 bottom: 0;
6034 right: 5px;
6035 margin-bottom: -5px;
6036 border-width: 5px 5px 0;
6037 border-top-color: #000;
6038 }
6039 .tooltip.top-right .tooltip-arrow {
6040 bottom: 0;
6041 left: 5px;
6042 margin-bottom: -5px;
6043 border-width: 5px 5px 0;
6044 border-top-color: #000;
6045 }
6046 .tooltip.right .tooltip-arrow {
6047 top: 50%;
6048 left: 0;
6049 margin-top: -5px;
6050 border-width: 5px 5px 5px 0;
6051 border-right-color: #000;
6052 }
6053 .tooltip.left .tooltip-arrow {
6054 top: 50%;
6055 right: 0;
6056 margin-top: -5px;
6057 border-width: 5px 0 5px 5px;
6058 border-left-color: #000;
6059 }
6060 .tooltip.bottom .tooltip-arrow {
6061 top: 0;
6062 left: 50%;
6063 margin-left: -5px;
6064 border-width: 0 5px 5px;
6065 border-bottom-color: #000;
6066 }
6067 .tooltip.bottom-left .tooltip-arrow {
6068 top: 0;
6069 right: 5px;
6070 margin-top: -5px;
6071 border-width: 0 5px 5px;
6072 border-bottom-color: #000;
6073 }
6074 .tooltip.bottom-right .tooltip-arrow {
6075 top: 0;
6076 left: 5px;
6077 margin-top: -5px;
6078 border-width: 0 5px 5px;
6079 border-bottom-color: #000;
6080 }
6081 .popover {
6082 position: absolute;
6083 top: 0;
6084 left: 0;
6085 z-index: 1060;
6086 display: none;
6087 max-width: 276px;
6088 padding: 1px;
6089 font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
6090 font-style: normal;
6091 font-weight: normal;
6092 letter-spacing: normal;
6093 line-break: auto;
6094 line-height: 1.42857143;
6095 text-align: left;
6096 text-align: start;
6097 text-decoration: none;
6098 text-shadow: none;
6099 text-transform: none;
6100 white-space: normal;
6101 word-break: normal;
6102 word-spacing: normal;
6103 word-wrap: normal;
6104 font-size: 13px;
6105 background-color: #fff;
6106 background-clip: padding-box;
6107 border: 1px solid #ccc;
6108 border: 1px solid rgba(0, 0, 0, 0.2);
6109 border-radius: 3px;
6110 -webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);
6111 box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);
6112 }
6113 .popover.top {
6114 margin-top: -10px;
6115 }
6116 .popover.right {
6117 margin-left: 10px;
6118 }
6119 .popover.bottom {
6120 margin-top: 10px;
6121 }
6122 .popover.left {
6123 margin-left: -10px;
6124 }
6125 .popover-title {
6126 margin: 0;
6127 padding: 8px 14px;
6128 font-size: 13px;
6129 background-color: #f7f7f7;
6130 border-bottom: 1px solid #ebebeb;
6131 border-radius: 2px 2px 0 0;
6132 }
6133 .popover-content {
6134 padding: 9px 14px;
6135 }
6136 .popover > .arrow,
6137 .popover > .arrow:after {
6138 position: absolute;
6139 display: block;
6140 width: 0;
6141 height: 0;
6142 border-color: transparent;
6143 border-style: solid;
6144 }
6145 .popover > .arrow {
6146 border-width: 11px;
6147 }
6148 .popover > .arrow:after {
6149 border-width: 10px;
6150 content: "";
6151 }
6152 .popover.top > .arrow {
6153 left: 50%;
6154 margin-left: -11px;
6155 border-bottom-width: 0;
6156 border-top-color: #999999;
6157 border-top-color: rgba(0, 0, 0, 0.25);
6158 bottom: -11px;
6159 }
6160 .popover.top > .arrow:after {
6161 content: " ";
6162 bottom: 1px;
6163 margin-left: -10px;
6164 border-bottom-width: 0;
6165 border-top-color: #fff;
6166 }
6167 .popover.right > .arrow {
6168 top: 50%;
6169 left: -11px;
6170 margin-top: -11px;
6171 border-left-width: 0;
6172 border-right-color: #999999;
6173 border-right-color: rgba(0, 0, 0, 0.25);
6174 }
6175 .popover.right > .arrow:after {
6176 content: " ";
6177 left: 1px;
6178 bottom: -10px;
6179 border-left-width: 0;
6180 border-right-color: #fff;
6181 }
6182 .popover.bottom > .arrow {
6183 left: 50%;
6184 margin-left: -11px;
6185 border-top-width: 0;
6186 border-bottom-color: #999999;
6187 border-bottom-color: rgba(0, 0, 0, 0.25);
6188 top: -11px;
6189 }
6190 .popover.bottom > .arrow:after {
6191 content: " ";
6192 top: 1px;
6193 margin-left: -10px;
6194 border-top-width: 0;
6195 border-bottom-color: #fff;
6196 }
6197 .popover.left > .arrow {
6198 top: 50%;
6199 right: -11px;
6200 margin-top: -11px;
6201 border-right-width: 0;
6202 border-left-color: #999999;
6203 border-left-color: rgba(0, 0, 0, 0.25);
6204 }
6205 .popover.left > .arrow:after {
6206 content: " ";
6207 right: 1px;
6208 border-right-width: 0;
6209 border-left-color: #fff;
6210 bottom: -10px;
6211 }
6212 .carousel {
6213 position: relative;
6214 }
6215 .carousel-inner {
6216 position: relative;
6217 overflow: hidden;
6218 width: 100%;
6219 }
6220 .carousel-inner > .item {
6221 display: none;
6222 position: relative;
6223 -webkit-transition: 0.6s ease-in-out left;
6224 -o-transition: 0.6s ease-in-out left;
6225 transition: 0.6s ease-in-out left;
6226 }
6227 .carousel-inner > .item > img,
6228 .carousel-inner > .item > a > img {
6229 line-height: 1;
6230 }
6231 @media all and (transform-3d), (-webkit-transform-3d) {
6232 .carousel-inner > .item {
6233 -webkit-transition: -webkit-transform 0.6s ease-in-out;
6234 -moz-transition: -moz-transform 0.6s ease-in-out;
6235 -o-transition: -o-transform 0.6s ease-in-out;
6236 transition: transform 0.6s ease-in-out;
6237 -webkit-backface-visibility: hidden;
6238 -moz-backface-visibility: hidden;
6239 backface-visibility: hidden;
6240 -webkit-perspective: 1000px;
6241 -moz-perspective: 1000px;
6242 perspective: 1000px;
6243 }
6244 .carousel-inner > .item.next,
6245 .carousel-inner > .item.active.right {
6246 -webkit-transform: translate3d(100%, 0, 0);
6247 transform: translate3d(100%, 0, 0);
6248 left: 0;
6249 }
6250 .carousel-inner > .item.prev,
6251 .carousel-inner > .item.active.left {
6252 -webkit-transform: translate3d(-100%, 0, 0);
6253 transform: translate3d(-100%, 0, 0);
6254 left: 0;
6255 }
6256 .carousel-inner > .item.next.left,
6257 .carousel-inner > .item.prev.right,
6258 .carousel-inner > .item.active {
6259 -webkit-transform: translate3d(0, 0, 0);
6260 transform: translate3d(0, 0, 0);
6261 left: 0;
6262 }
6263 }
6264 .carousel-inner > .active,
6265 .carousel-inner > .next,
6266 .carousel-inner > .prev {
6267 display: block;
6268 }
6269 .carousel-inner > .active {
6270 left: 0;
6271 }
6272 .carousel-inner > .next,
6273 .carousel-inner > .prev {
6274 position: absolute;
6275 top: 0;
6276 width: 100%;
6277 }
6278 .carousel-inner > .next {
6279 left: 100%;
6280 }
6281 .carousel-inner > .prev {
6282 left: -100%;
6283 }
6284 .carousel-inner > .next.left,
6285 .carousel-inner > .prev.right {
6286 left: 0;
6287 }
6288 .carousel-inner > .active.left {
6289 left: -100%;
6290 }
6291 .carousel-inner > .active.right {
6292 left: 100%;
6293 }
6294 .carousel-control {
6295 position: absolute;
6296 top: 0;
6297 left: 0;
6298 bottom: 0;
6299 width: 15%;
6300 opacity: 0.5;
6301 filter: alpha(opacity=50);
6302 font-size: 20px;
6303 color: #fff;
6304 text-align: center;
6305 text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);
6306 background-color: rgba(0, 0, 0, 0);
6307 }
6308 .carousel-control.left {
6309 background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);
6310 background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);
6311 background-image: linear-gradient(to right, rgba(0, 0, 0, 0.5) 0%, rgba(0, 0, 0, 0.0001) 100%);
6312 background-repeat: repeat-x;
6313 filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000', endColorstr='#00000000', GradientType=1);
6314 }
6315 .carousel-control.right {
6316 left: auto;
6317 right: 0;
6318 background-image: -webkit-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);
6319 background-image: -o-linear-gradient(left, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);
6320 background-image: linear-gradient(to right, rgba(0, 0, 0, 0.0001) 0%, rgba(0, 0, 0, 0.5) 100%);
6321 background-repeat: repeat-x;
6322 filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000', endColorstr='#80000000', GradientType=1);
6323 }
6324 .carousel-control:hover,
6325 .carousel-control:focus {
6326 outline: 0;
6327 color: #fff;
6328 text-decoration: none;
6329 opacity: 0.9;
6330 filter: alpha(opacity=90);
6331 }
6332 .carousel-control .icon-prev,
6333 .carousel-control .icon-next,
6334 .carousel-control .glyphicon-chevron-left,
6335 .carousel-control .glyphicon-chevron-right {
6336 position: absolute;
6337 top: 50%;
6338 margin-top: -10px;
6339 z-index: 5;
6340 display: inline-block;
6341 }
6342 .carousel-control .icon-prev,
6343 .carousel-control .glyphicon-chevron-left {
6344 left: 50%;
6345 margin-left: -10px;
6346 }
6347 .carousel-control .icon-next,
6348 .carousel-control .glyphicon-chevron-right {
6349 right: 50%;
6350 margin-right: -10px;
6351 }
6352 .carousel-control .icon-prev,
6353 .carousel-control .icon-next {
6354 width: 20px;
6355 height: 20px;
6356 line-height: 1;
6357 font-family: serif;
6358 }
6359 .carousel-control .icon-prev:before {
6360 content: '\2039';
6361 }
6362 .carousel-control .icon-next:before {
6363 content: '\203a';
6364 }
6365 .carousel-indicators {
6366 position: absolute;
6367 bottom: 10px;
6368 left: 50%;
6369 z-index: 15;
6370 width: 60%;
6371 margin-left: -30%;
6372 padding-left: 0;
6373 list-style: none;
6374 text-align: center;
6375 }
6376 .carousel-indicators li {
6377 display: inline-block;
6378 width: 10px;
6379 height: 10px;
6380 margin: 1px;
6381 text-indent: -999px;
6382 border: 1px solid #fff;
6383 border-radius: 10px;
6384 cursor: pointer;
6385 background-color: #000 \9;
6386 background-color: rgba(0, 0, 0, 0);
6387 }
6388 .carousel-indicators .active {
6389 margin: 0;
6390 width: 12px;
6391 height: 12px;
6392 background-color: #fff;
6393 }
6394 .carousel-caption {
6395 position: absolute;
6396 left: 15%;
6397 right: 15%;
6398 bottom: 20px;
6399 z-index: 10;
6400 padding-top: 20px;
6401 padding-bottom: 20px;
6402 color: #fff;
6403 text-align: center;
6404 text-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);
6405 }
6406 .carousel-caption .btn {
6407 text-shadow: none;
6408 }
6409 @media screen and (min-width: 768px) {
6410 .carousel-control .glyphicon-chevron-left,
6411 .carousel-control .glyphicon-chevron-right,
6412 .carousel-control .icon-prev,
6413 .carousel-control .icon-next {
6414 width: 30px;
6415 height: 30px;
6416 margin-top: -10px;
6417 font-size: 30px;
6418 }
6419 .carousel-control .glyphicon-chevron-left,
6420 .carousel-control .icon-prev {
6421 margin-left: -10px;
6422 }
6423 .carousel-control .glyphicon-chevron-right,
6424 .carousel-control .icon-next {
6425 margin-right: -10px;
6426 }
6427 .carousel-caption {
6428 left: 20%;
6429 right: 20%;
6430 padding-bottom: 30px;
6431 }
6432 .carousel-indicators {
6433 bottom: 20px;
6434 }
6435 }
6436 .clearfix:before,
6437 .clearfix:after,
6438 .dl-horizontal dd:before,
6439 .dl-horizontal dd:after,
6440 .container:before,
6441 .container:after,
6442 .container-fluid:before,
6443 .container-fluid:after,
6444 .row:before,
6445 .row:after,
6446 .form-horizontal .form-group:before,
6447 .form-horizontal .form-group:after,
6448 .btn-toolbar:before,
6449 .btn-toolbar:after,
6450 .btn-group-vertical > .btn-group:before,
6451 .btn-group-vertical > .btn-group:after,
6452 .nav:before,
6453 .nav:after,
6454 .navbar:before,
6455 .navbar:after,
6456 .navbar-header:before,
6457 .navbar-header:after,
6458 .navbar-collapse:before,
6459 .navbar-collapse:after,
6460 .pager:before,
6461 .pager:after,
6462 .panel-body:before,
6463 .panel-body:after,
6464 .modal-header:before,
6465 .modal-header:after,
6466 .modal-footer:before,
6467 .modal-footer:after,
6468 .item_buttons:before,
6469 .item_buttons:after {
6470 content: " ";
6471 display: table;
6472 }
6473 .clearfix:after,
6474 .dl-horizontal dd:after,
6475 .container:after,
6476 .container-fluid:after,
6477 .row:after,
6478 .form-horizontal .form-group:after,
6479 .btn-toolbar:after,
6480 .btn-group-vertical > .btn-group:after,
6481 .nav:after,
6482 .navbar:after,
6483 .navbar-header:after,
6484 .navbar-collapse:after,
6485 .pager:after,
6486 .panel-body:after,
6487 .modal-header:after,
6488 .modal-footer:after,
6489 .item_buttons:after {
6490 clear: both;
6491 }
6492 .center-block {
6493 display: block;
6494 margin-left: auto;
6495 margin-right: auto;
6496 }
6497 .pull-right {
6498 float: right !important;
6499 }
6500 .pull-left {
6501 float: left !important;
6502 }
6503 .hide {
6504 display: none !important;
6505 }
6506 .show {
6507 display: block !important;
6508 }
6509 .invisible {
6510 visibility: hidden;
6511 }
6512 .text-hide {
6513 font: 0/0 a;
6514 color: transparent;
6515 text-shadow: none;
6516 background-color: transparent;
6517 border: 0;
6518 }
6519 .hidden {
6520 display: none !important;
6521 }
6522 .affix {
6523 position: fixed;
6524 }
6525 @-ms-viewport {
6526 width: device-width;
6527 }
6528 .visible-xs,
6529 .visible-sm,
6530 .visible-md,
6531 .visible-lg {
6532 display: none !important;
6533 }
6534 .visible-xs-block,
6535 .visible-xs-inline,
6536 .visible-xs-inline-block,
6537 .visible-sm-block,
6538 .visible-sm-inline,
6539 .visible-sm-inline-block,
6540 .visible-md-block,
6541 .visible-md-inline,
6542 .visible-md-inline-block,
6543 .visible-lg-block,
6544 .visible-lg-inline,
6545 .visible-lg-inline-block {
6546 display: none !important;
6547 }
6548 @media (max-width: 767px) {
6549 .visible-xs {
6550 display: block !important;
6551 }
6552 table.visible-xs {
6553 display: table !important;
6554 }
6555 tr.visible-xs {
6556 display: table-row !important;
6557 }
6558 th.visible-xs,
6559 td.visible-xs {
6560 display: table-cell !important;
6561 }
6562 }
6563 @media (max-width: 767px) {
6564 .visible-xs-block {
6565 display: block !important;
6566 }
6567 }
6568 @media (max-width: 767px) {
6569 .visible-xs-inline {
6570 display: inline !important;
6571 }
6572 }
6573 @media (max-width: 767px) {
6574 .visible-xs-inline-block {
6575 display: inline-block !important;
6576 }
6577 }
6578 @media (min-width: 768px) and (max-width: 991px) {
6579 .visible-sm {
6580 display: block !important;
6581 }
6582 table.visible-sm {
6583 display: table !important;
6584 }
6585 tr.visible-sm {
6586 display: table-row !important;
6587 }
6588 th.visible-sm,
6589 td.visible-sm {
6590 display: table-cell !important;
6591 }
6592 }
6593 @media (min-width: 768px) and (max-width: 991px) {
6594 .visible-sm-block {
6595 display: block !important;
6596 }
6597 }
6598 @media (min-width: 768px) and (max-width: 991px) {
6599 .visible-sm-inline {
6600 display: inline !important;
6601 }
6602 }
6603 @media (min-width: 768px) and (max-width: 991px) {
6604 .visible-sm-inline-block {
6605 display: inline-block !important;
6606 }
6607 }
6608 @media (min-width: 992px) and (max-width: 1199px) {
6609 .visible-md {
6610 display: block !important;
6611 }
6612 table.visible-md {
6613 display: table !important;
6614 }
6615 tr.visible-md {
6616 display: table-row !important;
6617 }
6618 th.visible-md,
6619 td.visible-md {
6620 display: table-cell !important;
6621 }
6622 }
6623 @media (min-width: 992px) and (max-width: 1199px) {
6624 .visible-md-block {
6625 display: block !important;
6626 }
6627 }
6628 @media (min-width: 992px) and (max-width: 1199px) {
6629 .visible-md-inline {
6630 display: inline !important;
6631 }
6632 }
6633 @media (min-width: 992px) and (max-width: 1199px) {
6634 .visible-md-inline-block {
6635 display: inline-block !important;
6636 }
6637 }
6638 @media (min-width: 1200px) {
6639 .visible-lg {
6640 display: block !important;
6641 }
6642 table.visible-lg {
6643 display: table !important;
6644 }
6645 tr.visible-lg {
6646 display: table-row !important;
6647 }
6648 th.visible-lg,
6649 td.visible-lg {
6650 display: table-cell !important;
6651 }
6652 }
6653 @media (min-width: 1200px) {
6654 .visible-lg-block {
6655 display: block !important;
6656 }
6657 }
6658 @media (min-width: 1200px) {
6659 .visible-lg-inline {
6660 display: inline !important;
6661 }
6662 }
6663 @media (min-width: 1200px) {
6664 .visible-lg-inline-block {
6665 display: inline-block !important;
6666 }
6667 }
6668 @media (max-width: 767px) {
6669 .hidden-xs {
6670 display: none !important;
6671 }
6672 }
6673 @media (min-width: 768px) and (max-width: 991px) {
6674 .hidden-sm {
6675 display: none !important;
6676 }
6677 }
6678 @media (min-width: 992px) and (max-width: 1199px) {
6679 .hidden-md {
6680 display: none !important;
6681 }
6682 }
6683 @media (min-width: 1200px) {
6684 .hidden-lg {
6685 display: none !important;
6686 }
6687 }
6688 .visible-print {
6689 display: none !important;
6690 }
6691 @media print {
6692 .visible-print {
6693 display: block !important;
6694 }
6695 table.visible-print {
6696 display: table !important;
6697 }
6698 tr.visible-print {
6699 display: table-row !important;
6700 }
6701 th.visible-print,
6702 td.visible-print {
6703 display: table-cell !important;
6704 }
6705 }
6706 .visible-print-block {
6707 display: none !important;
6708 }
6709 @media print {
6710 .visible-print-block {
6711 display: block !important;
6712 }
6713 }
6714 .visible-print-inline {
6715 display: none !important;
6716 }
6717 @media print {
6718 .visible-print-inline {
6719 display: inline !important;
6720 }
6721 }
6722 .visible-print-inline-block {
6723 display: none !important;
6724 }
6725 @media print {
6726 .visible-print-inline-block {
6727 display: inline-block !important;
6728 }
6729 }
6730 @media print {
6731 .hidden-print {
6732 display: none !important;
6733 }
6734 }
6735 /*!
6736 *
6737 * Font Awesome
6738 *
6739 */
6740 /*!
6741 * Font Awesome 4.2.0 by @davegandy - http://fontawesome.io - @fontawesome
6742 * License - http://fontawesome.io/license (Font: SIL OFL 1.1, CSS: MIT License)
6743 */
6744 /* FONT PATH
6745 * -------------------------- */
6746 @font-face {
6747 font-family: 'FontAwesome';
6748 src: url('../components/font-awesome/fonts/fontawesome-webfont.eot?v=4.2.0');
6749 src: url('../components/font-awesome/fonts/fontawesome-webfont.eot?#iefix&v=4.2.0') format('embedded-opentype'), url('../components/font-awesome/fonts/fontawesome-webfont.woff?v=4.2.0') format('woff'), url('../components/font-awesome/fonts/fontawesome-webfont.ttf?v=4.2.0') format('truetype'), url('../components/font-awesome/fonts/fontawesome-webfont.svg?v=4.2.0#fontawesomeregular') format('svg');
6750 font-weight: normal;
6751 font-style: normal;
6752 }
6753 .fa {
6754 display: inline-block;
6755 font: normal normal normal 14px/1 FontAwesome;
6756 font-size: inherit;
6757 text-rendering: auto;
6758 -webkit-font-smoothing: antialiased;
6759 -moz-osx-font-smoothing: grayscale;
6760 }
6761 /* makes the font 33% larger relative to the icon container */
6762 .fa-lg {
6763 font-size: 1.33333333em;
6764 line-height: 0.75em;
6765 vertical-align: -15%;
6766 }
6767 .fa-2x {
6768 font-size: 2em;
6769 }
6770 .fa-3x {
6771 font-size: 3em;
6772 }
6773 .fa-4x {
6774 font-size: 4em;
6775 }
6776 .fa-5x {
6777 font-size: 5em;
6778 }
6779 .fa-fw {
6780 width: 1.28571429em;
6781 text-align: center;
6782 }
6783 .fa-ul {
6784 padding-left: 0;
6785 margin-left: 2.14285714em;
6786 list-style-type: none;
6787 }
6788 .fa-ul > li {
6789 position: relative;
6790 }
6791 .fa-li {
6792 position: absolute;
6793 left: -2.14285714em;
6794 width: 2.14285714em;
6795 top: 0.14285714em;
6796 text-align: center;
6797 }
6798 .fa-li.fa-lg {
6799 left: -1.85714286em;
6800 }
6801 .fa-border {
6802 padding: .2em .25em .15em;
6803 border: solid 0.08em #eee;
6804 border-radius: .1em;
6805 }
6806 .pull-right {
6807 float: right;
6808 }
6809 .pull-left {
6810 float: left;
6811 }
6812 .fa.pull-left {
6813 margin-right: .3em;
6814 }
6815 .fa.pull-right {
6816 margin-left: .3em;
6817 }
6818 .fa-spin {
6819 -webkit-animation: fa-spin 2s infinite linear;
6820 animation: fa-spin 2s infinite linear;
6821 }
6822 @-webkit-keyframes fa-spin {
6823 0% {
6824 -webkit-transform: rotate(0deg);
6825 transform: rotate(0deg);
6826 }
6827 100% {
6828 -webkit-transform: rotate(359deg);
6829 transform: rotate(359deg);
6830 }
6831 }
6832 @keyframes fa-spin {
6833 0% {
6834 -webkit-transform: rotate(0deg);
6835 transform: rotate(0deg);
6836 }
6837 100% {
6838 -webkit-transform: rotate(359deg);
6839 transform: rotate(359deg);
6840 }
6841 }
6842 .fa-rotate-90 {
6843 filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=1);
6844 -webkit-transform: rotate(90deg);
6845 -ms-transform: rotate(90deg);
6846 transform: rotate(90deg);
6847 }
6848 .fa-rotate-180 {
6849 filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=2);
6850 -webkit-transform: rotate(180deg);
6851 -ms-transform: rotate(180deg);
6852 transform: rotate(180deg);
6853 }
6854 .fa-rotate-270 {
6855 filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=3);
6856 -webkit-transform: rotate(270deg);
6857 -ms-transform: rotate(270deg);
6858 transform: rotate(270deg);
6859 }
6860 .fa-flip-horizontal {
6861 filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1);
6862 -webkit-transform: scale(-1, 1);
6863 -ms-transform: scale(-1, 1);
6864 transform: scale(-1, 1);
6865 }
6866 .fa-flip-vertical {
6867 filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1);
6868 -webkit-transform: scale(1, -1);
6869 -ms-transform: scale(1, -1);
6870 transform: scale(1, -1);
6871 }
6872 :root .fa-rotate-90,
6873 :root .fa-rotate-180,
6874 :root .fa-rotate-270,
6875 :root .fa-flip-horizontal,
6876 :root .fa-flip-vertical {
6877 filter: none;
6878 }
6879 .fa-stack {
6880 position: relative;
6881 display: inline-block;
6882 width: 2em;
6883 height: 2em;
6884 line-height: 2em;
6885 vertical-align: middle;
6886 }
6887 .fa-stack-1x,
6888 .fa-stack-2x {
6889 position: absolute;
6890 left: 0;
6891 width: 100%;
6892 text-align: center;
6893 }
6894 .fa-stack-1x {
6895 line-height: inherit;
6896 }
6897 .fa-stack-2x {
6898 font-size: 2em;
6899 }
6900 .fa-inverse {
6901 color: #fff;
6902 }
6903 /* Font Awesome uses the Unicode Private Use Area (PUA) to ensure screen
6904 readers do not read off random characters that represent icons */
6905 .fa-glass:before {
6906 content: "\f000";
6907 }
6908 .fa-music:before {
6909 content: "\f001";
6910 }
6911 .fa-search:before {
6912 content: "\f002";
6913 }
6914 .fa-envelope-o:before {
6915 content: "\f003";
6916 }
6917 .fa-heart:before {
6918 content: "\f004";
6919 }
6920 .fa-star:before {
6921 content: "\f005";
6922 }
6923 .fa-star-o:before {
6924 content: "\f006";
6925 }
6926 .fa-user:before {
6927 content: "\f007";
6928 }
6929 .fa-film:before {
6930 content: "\f008";
6931 }
6932 .fa-th-large:before {
6933 content: "\f009";
6934 }
6935 .fa-th:before {
6936 content: "\f00a";
6937 }
6938 .fa-th-list:before {
6939 content: "\f00b";
6940 }
6941 .fa-check:before {
6942 content: "\f00c";
6943 }
6944 .fa-remove:before,
6945 .fa-close:before,
6946 .fa-times:before {
6947 content: "\f00d";
6948 }
6949 .fa-search-plus:before {
6950 content: "\f00e";
6951 }
6952 .fa-search-minus:before {
6953 content: "\f010";
6954 }
6955 .fa-power-off:before {
6956 content: "\f011";
6957 }
6958 .fa-signal:before {
6959 content: "\f012";
6960 }
6961 .fa-gear:before,
6962 .fa-cog:before {
6963 content: "\f013";
6964 }
6965 .fa-trash-o:before {
6966 content: "\f014";
6967 }
6968 .fa-home:before {
6969 content: "\f015";
6970 }
6971 .fa-file-o:before {
6972 content: "\f016";
6973 }
6974 .fa-clock-o:before {
6975 content: "\f017";
6976 }
6977 .fa-road:before {
6978 content: "\f018";
6979 }
6980 .fa-download:before {
6981 content: "\f019";
6982 }
6983 .fa-arrow-circle-o-down:before {
6984 content: "\f01a";
6985 }
6986 .fa-arrow-circle-o-up:before {
6987 content: "\f01b";
6988 }
6989 .fa-inbox:before {
6990 content: "\f01c";
6991 }
6992 .fa-play-circle-o:before {
6993 content: "\f01d";
6994 }
6995 .fa-rotate-right:before,
6996 .fa-repeat:before {
6997 content: "\f01e";
6998 }
6999 .fa-refresh:before {
7000 content: "\f021";
7001 }
7002 .fa-list-alt:before {
7003 content: "\f022";
7004 }
7005 .fa-lock:before {
7006 content: "\f023";
7007 }
7008 .fa-flag:before {
7009 content: "\f024";
7010 }
7011 .fa-headphones:before {
7012 content: "\f025";
7013 }
7014 .fa-volume-off:before {
7015 content: "\f026";
7016 }
7017 .fa-volume-down:before {
7018 content: "\f027";
7019 }
7020 .fa-volume-up:before {
7021 content: "\f028";
7022 }
7023 .fa-qrcode:before {
7024 content: "\f029";
7025 }
7026 .fa-barcode:before {
7027 content: "\f02a";
7028 }
7029 .fa-tag:before {
7030 content: "\f02b";
7031 }
7032 .fa-tags:before {
7033 content: "\f02c";
7034 }
7035 .fa-book:before {
7036 content: "\f02d";
7037 }
7038 .fa-bookmark:before {
7039 content: "\f02e";
7040 }
7041 .fa-print:before {
7042 content: "\f02f";
7043 }
7044 .fa-camera:before {
7045 content: "\f030";
7046 }
7047 .fa-font:before {
7048 content: "\f031";
7049 }
7050 .fa-bold:before {
7051 content: "\f032";
7052 }
7053 .fa-italic:before {
7054 content: "\f033";
7055 }
7056 .fa-text-height:before {
7057 content: "\f034";
7058 }
7059 .fa-text-width:before {
7060 content: "\f035";
7061 }
7062 .fa-align-left:before {
7063 content: "\f036";
7064 }
7065 .fa-align-center:before {
7066 content: "\f037";
7067 }
7068 .fa-align-right:before {
7069 content: "\f038";
7070 }
7071 .fa-align-justify:before {
7072 content: "\f039";
7073 }
7074 .fa-list:before {
7075 content: "\f03a";
7076 }
7077 .fa-dedent:before,
7078 .fa-outdent:before {
7079 content: "\f03b";
7080 }
7081 .fa-indent:before {
7082 content: "\f03c";
7083 }
7084 .fa-video-camera:before {
7085 content: "\f03d";
7086 }
7087 .fa-photo:before,
7088 .fa-image:before,
7089 .fa-picture-o:before {
7090 content: "\f03e";
7091 }
7092 .fa-pencil:before {
7093 content: "\f040";
7094 }
7095 .fa-map-marker:before {
7096 content: "\f041";
7097 }
7098 .fa-adjust:before {
7099 content: "\f042";
7100 }
7101 .fa-tint:before {
7102 content: "\f043";
7103 }
7104 .fa-edit:before,
7105 .fa-pencil-square-o:before {
7106 content: "\f044";
7107 }
7108 .fa-share-square-o:before {
7109 content: "\f045";
7110 }
7111 .fa-check-square-o:before {
7112 content: "\f046";
7113 }
7114 .fa-arrows:before {
7115 content: "\f047";
7116 }
7117 .fa-step-backward:before {
7118 content: "\f048";
7119 }
7120 .fa-fast-backward:before {
7121 content: "\f049";
7122 }
7123 .fa-backward:before {
7124 content: "\f04a";
7125 }
7126 .fa-play:before {
7127 content: "\f04b";
7128 }
7129 .fa-pause:before {
7130 content: "\f04c";
7131 }
7132 .fa-stop:before {
7133 content: "\f04d";
7134 }
7135 .fa-forward:before {
7136 content: "\f04e";
7137 }
7138 .fa-fast-forward:before {
7139 content: "\f050";
7140 }
7141 .fa-step-forward:before {
7142 content: "\f051";
7143 }
7144 .fa-eject:before {
7145 content: "\f052";
7146 }
7147 .fa-chevron-left:before {
7148 content: "\f053";
7149 }
7150 .fa-chevron-right:before {
7151 content: "\f054";
7152 }
7153 .fa-plus-circle:before {
7154 content: "\f055";
7155 }
7156 .fa-minus-circle:before {
7157 content: "\f056";
7158 }
7159 .fa-times-circle:before {
7160 content: "\f057";
7161 }
7162 .fa-check-circle:before {
7163 content: "\f058";
7164 }
7165 .fa-question-circle:before {
7166 content: "\f059";
7167 }
7168 .fa-info-circle:before {
7169 content: "\f05a";
7170 }
7171 .fa-crosshairs:before {
7172 content: "\f05b";
7173 }
7174 .fa-times-circle-o:before {
7175 content: "\f05c";
7176 }
7177 .fa-check-circle-o:before {
7178 content: "\f05d";
7179 }
7180 .fa-ban:before {
7181 content: "\f05e";
7182 }
7183 .fa-arrow-left:before {
7184 content: "\f060";
7185 }
7186 .fa-arrow-right:before {
7187 content: "\f061";
7188 }
7189 .fa-arrow-up:before {
7190 content: "\f062";
7191 }
7192 .fa-arrow-down:before {
7193 content: "\f063";
7194 }
7195 .fa-mail-forward:before,
7196 .fa-share:before {
7197 content: "\f064";
7198 }
7199 .fa-expand:before {
7200 content: "\f065";
7201 }
7202 .fa-compress:before {
7203 content: "\f066";
7204 }
7205 .fa-plus:before {
7206 content: "\f067";
7207 }
7208 .fa-minus:before {
7209 content: "\f068";
7210 }
7211 .fa-asterisk:before {
7212 content: "\f069";
7213 }
7214 .fa-exclamation-circle:before {
7215 content: "\f06a";
7216 }
7217 .fa-gift:before {
7218 content: "\f06b";
7219 }
7220 .fa-leaf:before {
7221 content: "\f06c";
7222 }
7223 .fa-fire:before {
7224 content: "\f06d";
7225 }
7226 .fa-eye:before {
7227 content: "\f06e";
7228 }
7229 .fa-eye-slash:before {
7230 content: "\f070";
7231 }
7232 .fa-warning:before,
7233 .fa-exclamation-triangle:before {
7234 content: "\f071";
7235 }
7236 .fa-plane:before {
7237 content: "\f072";
7238 }
7239 .fa-calendar:before {
7240 content: "\f073";
7241 }
7242 .fa-random:before {
7243 content: "\f074";
7244 }
7245 .fa-comment:before {
7246 content: "\f075";
7247 }
7248 .fa-magnet:before {
7249 content: "\f076";
7250 }
7251 .fa-chevron-up:before {
7252 content: "\f077";
7253 }
7254 .fa-chevron-down:before {
7255 content: "\f078";
7256 }
7257 .fa-retweet:before {
7258 content: "\f079";
7259 }
7260 .fa-shopping-cart:before {
7261 content: "\f07a";
7262 }
7263 .fa-folder:before {
7264 content: "\f07b";
7265 }
7266 .fa-folder-open:before {
7267 content: "\f07c";
7268 }
7269 .fa-arrows-v:before {
7270 content: "\f07d";
7271 }
7272 .fa-arrows-h:before {
7273 content: "\f07e";
7274 }
7275 .fa-bar-chart-o:before,
7276 .fa-bar-chart:before {
7277 content: "\f080";
7278 }
7279 .fa-twitter-square:before {
7280 content: "\f081";
7281 }
7282 .fa-facebook-square:before {
7283 content: "\f082";
7284 }
7285 .fa-camera-retro:before {
7286 content: "\f083";
7287 }
7288 .fa-key:before {
7289 content: "\f084";
7290 }
7291 .fa-gears:before,
7292 .fa-cogs:before {
7293 content: "\f085";
7294 }
7295 .fa-comments:before {
7296 content: "\f086";
7297 }
7298 .fa-thumbs-o-up:before {
7299 content: "\f087";
7300 }
7301 .fa-thumbs-o-down:before {
7302 content: "\f088";
7303 }
7304 .fa-star-half:before {
7305 content: "\f089";
7306 }
7307 .fa-heart-o:before {
7308 content: "\f08a";
7309 }
7310 .fa-sign-out:before {
7311 content: "\f08b";
7312 }
7313 .fa-linkedin-square:before {
7314 content: "\f08c";
7315 }
7316 .fa-thumb-tack:before {
7317 content: "\f08d";
7318 }
7319 .fa-external-link:before {
7320 content: "\f08e";
7321 }
7322 .fa-sign-in:before {
7323 content: "\f090";
7324 }
7325 .fa-trophy:before {
7326 content: "\f091";
7327 }
7328 .fa-github-square:before {
7329 content: "\f092";
7330 }
7331 .fa-upload:before {
7332 content: "\f093";
7333 }
7334 .fa-lemon-o:before {
7335 content: "\f094";
7336 }
7337 .fa-phone:before {
7338 content: "\f095";
7339 }
7340 .fa-square-o:before {
7341 content: "\f096";
7342 }
7343 .fa-bookmark-o:before {
7344 content: "\f097";
7345 }
7346 .fa-phone-square:before {
7347 content: "\f098";
7348 }
7349 .fa-twitter:before {
7350 content: "\f099";
7351 }
7352 .fa-facebook:before {
7353 content: "\f09a";
7354 }
7355 .fa-github:before {
7356 content: "\f09b";
7357 }
7358 .fa-unlock:before {
7359 content: "\f09c";
7360 }
7361 .fa-credit-card:before {
7362 content: "\f09d";
7363 }
7364 .fa-rss:before {
7365 content: "\f09e";
7366 }
7367 .fa-hdd-o:before {
7368 content: "\f0a0";
7369 }
7370 .fa-bullhorn:before {
7371 content: "\f0a1";
7372 }
7373 .fa-bell:before {
7374 content: "\f0f3";
7375 }
7376 .fa-certificate:before {
7377 content: "\f0a3";
7378 }
7379 .fa-hand-o-right:before {
7380 content: "\f0a4";
7381 }
7382 .fa-hand-o-left:before {
7383 content: "\f0a5";
7384 }
7385 .fa-hand-o-up:before {
7386 content: "\f0a6";
7387 }
7388 .fa-hand-o-down:before {
7389 content: "\f0a7";
7390 }
7391 .fa-arrow-circle-left:before {
7392 content: "\f0a8";
7393 }
7394 .fa-arrow-circle-right:before {
7395 content: "\f0a9";
7396 }
7397 .fa-arrow-circle-up:before {
7398 content: "\f0aa";
7399 }
7400 .fa-arrow-circle-down:before {
7401 content: "\f0ab";
7402 }
7403 .fa-globe:before {
7404 content: "\f0ac";
7405 }
7406 .fa-wrench:before {
7407 content: "\f0ad";
7408 }
7409 .fa-tasks:before {
7410 content: "\f0ae";
7411 }
7412 .fa-filter:before {
7413 content: "\f0b0";
7414 }
7415 .fa-briefcase:before {
7416 content: "\f0b1";
7417 }
7418 .fa-arrows-alt:before {
7419 content: "\f0b2";
7420 }
7421 .fa-group:before,
7422 .fa-users:before {
7423 content: "\f0c0";
7424 }
7425 .fa-chain:before,
7426 .fa-link:before {
7427 content: "\f0c1";
7428 }
7429 .fa-cloud:before {
7430 content: "\f0c2";
7431 }
7432 .fa-flask:before {
7433 content: "\f0c3";
7434 }
7435 .fa-cut:before,
7436 .fa-scissors:before {
7437 content: "\f0c4";
7438 }
7439 .fa-copy:before,
7440 .fa-files-o:before {
7441 content: "\f0c5";
7442 }
7443 .fa-paperclip:before {
7444 content: "\f0c6";
7445 }
7446 .fa-save:before,
7447 .fa-floppy-o:before {
7448 content: "\f0c7";
7449 }
7450 .fa-square:before {
7451 content: "\f0c8";
7452 }
7453 .fa-navicon:before,
7454 .fa-reorder:before,
7455 .fa-bars:before {
7456 content: "\f0c9";
7457 }
7458 .fa-list-ul:before {
7459 content: "\f0ca";
7460 }
7461 .fa-list-ol:before {
7462 content: "\f0cb";
7463 }
7464 .fa-strikethrough:before {
7465 content: "\f0cc";
7466 }
7467 .fa-underline:before {
7468 content: "\f0cd";
7469 }
7470 .fa-table:before {
7471 content: "\f0ce";
7472 }
7473 .fa-magic:before {
7474 content: "\f0d0";
7475 }
7476 .fa-truck:before {
7477 content: "\f0d1";
7478 }
7479 .fa-pinterest:before {
7480 content: "\f0d2";
7481 }
7482 .fa-pinterest-square:before {
7483 content: "\f0d3";
7484 }
7485 .fa-google-plus-square:before {
7486 content: "\f0d4";
7487 }
7488 .fa-google-plus:before {
7489 content: "\f0d5";
7490 }
7491 .fa-money:before {
7492 content: "\f0d6";
7493 }
7494 .fa-caret-down:before {
7495 content: "\f0d7";
7496 }
7497 .fa-caret-up:before {
7498 content: "\f0d8";
7499 }
7500 .fa-caret-left:before {
7501 content: "\f0d9";
7502 }
7503 .fa-caret-right:before {
7504 content: "\f0da";
7505 }
7506 .fa-columns:before {
7507 content: "\f0db";
7508 }
7509 .fa-unsorted:before,
7510 .fa-sort:before {
7511 content: "\f0dc";
7512 }
7513 .fa-sort-down:before,
7514 .fa-sort-desc:before {
7515 content: "\f0dd";
7516 }
7517 .fa-sort-up:before,
7518 .fa-sort-asc:before {
7519 content: "\f0de";
7520 }
7521 .fa-envelope:before {
7522 content: "\f0e0";
7523 }
7524 .fa-linkedin:before {
7525 content: "\f0e1";
7526 }
7527 .fa-rotate-left:before,
7528 .fa-undo:before {
7529 content: "\f0e2";
7530 }
7531 .fa-legal:before,
7532 .fa-gavel:before {
7533 content: "\f0e3";
7534 }
7535 .fa-dashboard:before,
7536 .fa-tachometer:before {
7537 content: "\f0e4";
7538 }
7539 .fa-comment-o:before {
7540 content: "\f0e5";
7541 }
7542 .fa-comments-o:before {
7543 content: "\f0e6";
7544 }
7545 .fa-flash:before,
7546 .fa-bolt:before {
7547 content: "\f0e7";
7548 }
7549 .fa-sitemap:before {
7550 content: "\f0e8";
7551 }
7552 .fa-umbrella:before {
7553 content: "\f0e9";
7554 }
7555 .fa-paste:before,
7556 .fa-clipboard:before {
7557 content: "\f0ea";
7558 }
7559 .fa-lightbulb-o:before {
7560 content: "\f0eb";
7561 }
7562 .fa-exchange:before {
7563 content: "\f0ec";
7564 }
7565 .fa-cloud-download:before {
7566 content: "\f0ed";
7567 }
7568 .fa-cloud-upload:before {
7569 content: "\f0ee";
7570 }
7571 .fa-user-md:before {
7572 content: "\f0f0";
7573 }
7574 .fa-stethoscope:before {
7575 content: "\f0f1";
7576 }
7577 .fa-suitcase:before {
7578 content: "\f0f2";
7579 }
7580 .fa-bell-o:before {
7581 content: "\f0a2";
7582 }
7583 .fa-coffee:before {
7584 content: "\f0f4";
7585 }
7586 .fa-cutlery:before {
7587 content: "\f0f5";
7588 }
7589 .fa-file-text-o:before {
7590 content: "\f0f6";
7591 }
7592 .fa-building-o:before {
7593 content: "\f0f7";
7594 }
7595 .fa-hospital-o:before {
7596 content: "\f0f8";
7597 }
7598 .fa-ambulance:before {
7599 content: "\f0f9";
7600 }
7601 .fa-medkit:before {
7602 content: "\f0fa";
7603 }
7604 .fa-fighter-jet:before {
7605 content: "\f0fb";
7606 }
7607 .fa-beer:before {
7608 content: "\f0fc";
7609 }
7610 .fa-h-square:before {
7611 content: "\f0fd";
7612 }
7613 .fa-plus-square:before {
7614 content: "\f0fe";
7615 }
7616 .fa-angle-double-left:before {
7617 content: "\f100";
7618 }
7619 .fa-angle-double-right:before {
7620 content: "\f101";
7621 }
7622 .fa-angle-double-up:before {
7623 content: "\f102";
7624 }
7625 .fa-angle-double-down:before {
7626 content: "\f103";
7627 }
7628 .fa-angle-left:before {
7629 content: "\f104";
7630 }
7631 .fa-angle-right:before {
7632 content: "\f105";
7633 }
7634 .fa-angle-up:before {
7635 content: "\f106";
7636 }
7637 .fa-angle-down:before {
7638 content: "\f107";
7639 }
7640 .fa-desktop:before {
7641 content: "\f108";
7642 }
7643 .fa-laptop:before {
7644 content: "\f109";
7645 }
7646 .fa-tablet:before {
7647 content: "\f10a";
7648 }
7649 .fa-mobile-phone:before,
7650 .fa-mobile:before {
7651 content: "\f10b";
7652 }
7653 .fa-circle-o:before {
7654 content: "\f10c";
7655 }
7656 .fa-quote-left:before {
7657 content: "\f10d";
7658 }
7659 .fa-quote-right:before {
7660 content: "\f10e";
7661 }
7662 .fa-spinner:before {
7663 content: "\f110";
7664 }
7665 .fa-circle:before {
7666 content: "\f111";
7667 }
7668 .fa-mail-reply:before,
7669 .fa-reply:before {
7670 content: "\f112";
7671 }
7672 .fa-github-alt:before {
7673 content: "\f113";
7674 }
7675 .fa-folder-o:before {
7676 content: "\f114";
7677 }
7678 .fa-folder-open-o:before {
7679 content: "\f115";
7680 }
7681 .fa-smile-o:before {
7682 content: "\f118";
7683 }
7684 .fa-frown-o:before {
7685 content: "\f119";
7686 }
7687 .fa-meh-o:before {
7688 content: "\f11a";
7689 }
7690 .fa-gamepad:before {
7691 content: "\f11b";
7692 }
7693 .fa-keyboard-o:before {
7694 content: "\f11c";
7695 }
7696 .fa-flag-o:before {
7697 content: "\f11d";
7698 }
7699 .fa-flag-checkered:before {
7700 content: "\f11e";
7701 }
7702 .fa-terminal:before {
7703 content: "\f120";
7704 }
7705 .fa-code:before {
7706 content: "\f121";
7707 }
7708 .fa-mail-reply-all:before,
7709 .fa-reply-all:before {
7710 content: "\f122";
7711 }
7712 .fa-star-half-empty:before,
7713 .fa-star-half-full:before,
7714 .fa-star-half-o:before {
7715 content: "\f123";
7716 }
7717 .fa-location-arrow:before {
7718 content: "\f124";
7719 }
7720 .fa-crop:before {
7721 content: "\f125";
7722 }
7723 .fa-code-fork:before {
7724 content: "\f126";
7725 }
7726 .fa-unlink:before,
7727 .fa-chain-broken:before {
7728 content: "\f127";
7729 }
7730 .fa-question:before {
7731 content: "\f128";
7732 }
7733 .fa-info:before {
7734 content: "\f129";
7735 }
7736 .fa-exclamation:before {
7737 content: "\f12a";
7738 }
7739 .fa-superscript:before {
7740 content: "\f12b";
7741 }
7742 .fa-subscript:before {
7743 content: "\f12c";
7744 }
7745 .fa-eraser:before {
7746 content: "\f12d";
7747 }
7748 .fa-puzzle-piece:before {
7749 content: "\f12e";
7750 }
7751 .fa-microphone:before {
7752 content: "\f130";
7753 }
7754 .fa-microphone-slash:before {
7755 content: "\f131";
7756 }
7757 .fa-shield:before {
7758 content: "\f132";
7759 }
7760 .fa-calendar-o:before {
7761 content: "\f133";
7762 }
7763 .fa-fire-extinguisher:before {
7764 content: "\f134";
7765 }
7766 .fa-rocket:before {
7767 content: "\f135";
7768 }
7769 .fa-maxcdn:before {
7770 content: "\f136";
7771 }
7772 .fa-chevron-circle-left:before {
7773 content: "\f137";
7774 }
7775 .fa-chevron-circle-right:before {
7776 content: "\f138";
7777 }
7778 .fa-chevron-circle-up:before {
7779 content: "\f139";
7780 }
7781 .fa-chevron-circle-down:before {
7782 content: "\f13a";
7783 }
7784 .fa-html5:before {
7785 content: "\f13b";
7786 }
7787 .fa-css3:before {
7788 content: "\f13c";
7789 }
7790 .fa-anchor:before {
7791 content: "\f13d";
7792 }
7793 .fa-unlock-alt:before {
7794 content: "\f13e";
7795 }
7796 .fa-bullseye:before {
7797 content: "\f140";
7798 }
7799 .fa-ellipsis-h:before {
7800 content: "\f141";
7801 }
7802 .fa-ellipsis-v:before {
7803 content: "\f142";
7804 }
7805 .fa-rss-square:before {
7806 content: "\f143";
7807 }
7808 .fa-play-circle:before {
7809 content: "\f144";
7810 }
7811 .fa-ticket:before {
7812 content: "\f145";
7813 }
7814 .fa-minus-square:before {
7815 content: "\f146";
7816 }
7817 .fa-minus-square-o:before {
7818 content: "\f147";
7819 }
7820 .fa-level-up:before {
7821 content: "\f148";
7822 }
7823 .fa-level-down:before {
7824 content: "\f149";
7825 }
7826 .fa-check-square:before {
7827 content: "\f14a";
7828 }
7829 .fa-pencil-square:before {
7830 content: "\f14b";
7831 }
7832 .fa-external-link-square:before {
7833 content: "\f14c";
7834 }
7835 .fa-share-square:before {
7836 content: "\f14d";
7837 }
7838 .fa-compass:before {
7839 content: "\f14e";
7840 }
7841 .fa-toggle-down:before,
7842 .fa-caret-square-o-down:before {
7843 content: "\f150";
7844 }
7845 .fa-toggle-up:before,
7846 .fa-caret-square-o-up:before {
7847 content: "\f151";
7848 }
7849 .fa-toggle-right:before,
7850 .fa-caret-square-o-right:before {
7851 content: "\f152";
7852 }
7853 .fa-euro:before,
7854 .fa-eur:before {
7855 content: "\f153";
7856 }
7857 .fa-gbp:before {
7858 content: "\f154";
7859 }
7860 .fa-dollar:before,
7861 .fa-usd:before {
7862 content: "\f155";
7863 }
7864 .fa-rupee:before,
7865 .fa-inr:before {
7866 content: "\f156";
7867 }
7868 .fa-cny:before,
7869 .fa-rmb:before,
7870 .fa-yen:before,
7871 .fa-jpy:before {
7872 content: "\f157";
7873 }
7874 .fa-ruble:before,
7875 .fa-rouble:before,
7876 .fa-rub:before {
7877 content: "\f158";
7878 }
7879 .fa-won:before,
7880 .fa-krw:before {
7881 content: "\f159";
7882 }
7883 .fa-bitcoin:before,
7884 .fa-btc:before {
7885 content: "\f15a";
7886 }
7887 .fa-file:before {
7888 content: "\f15b";
7889 }
7890 .fa-file-text:before {
7891 content: "\f15c";
7892 }
7893 .fa-sort-alpha-asc:before {
7894 content: "\f15d";
7895 }
7896 .fa-sort-alpha-desc:before {
7897 content: "\f15e";
7898 }
7899 .fa-sort-amount-asc:before {
7900 content: "\f160";
7901 }
7902 .fa-sort-amount-desc:before {
7903 content: "\f161";
7904 }
7905 .fa-sort-numeric-asc:before {
7906 content: "\f162";
7907 }
7908 .fa-sort-numeric-desc:before {
7909 content: "\f163";
7910 }
7911 .fa-thumbs-up:before {
7912 content: "\f164";
7913 }
7914 .fa-thumbs-down:before {
7915 content: "\f165";
7916 }
7917 .fa-youtube-square:before {
7918 content: "\f166";
7919 }
7920 .fa-youtube:before {
7921 content: "\f167";
7922 }
7923 .fa-xing:before {
7924 content: "\f168";
7925 }
7926 .fa-xing-square:before {
7927 content: "\f169";
7928 }
7929 .fa-youtube-play:before {
7930 content: "\f16a";
7931 }
7932 .fa-dropbox:before {
7933 content: "\f16b";
7934 }
7935 .fa-stack-overflow:before {
7936 content: "\f16c";
7937 }
7938 .fa-instagram:before {
7939 content: "\f16d";
7940 }
7941 .fa-flickr:before {
7942 content: "\f16e";
7943 }
7944 .fa-adn:before {
7945 content: "\f170";
7946 }
7947 .fa-bitbucket:before {
7948 content: "\f171";
7949 }
7950 .fa-bitbucket-square:before {
7951 content: "\f172";
7952 }
7953 .fa-tumblr:before {
7954 content: "\f173";
7955 }
7956 .fa-tumblr-square:before {
7957 content: "\f174";
7958 }
7959 .fa-long-arrow-down:before {
7960 content: "\f175";
7961 }
7962 .fa-long-arrow-up:before {
7963 content: "\f176";
7964 }
7965 .fa-long-arrow-left:before {
7966 content: "\f177";
7967 }
7968 .fa-long-arrow-right:before {
7969 content: "\f178";
7970 }
7971 .fa-apple:before {
7972 content: "\f179";
7973 }
7974 .fa-windows:before {
7975 content: "\f17a";
7976 }
7977 .fa-android:before {
7978 content: "\f17b";
7979 }
7980 .fa-linux:before {
7981 content: "\f17c";
7982 }
7983 .fa-dribbble:before {
7984 content: "\f17d";
7985 }
7986 .fa-skype:before {
7987 content: "\f17e";
7988 }
7989 .fa-foursquare:before {
7990 content: "\f180";
7991 }
7992 .fa-trello:before {
7993 content: "\f181";
7994 }
7995 .fa-female:before {
7996 content: "\f182";
7997 }
7998 .fa-male:before {
7999 content: "\f183";
8000 }
8001 .fa-gittip:before {
8002 content: "\f184";
8003 }
8004 .fa-sun-o:before {
8005 content: "\f185";
8006 }
8007 .fa-moon-o:before {
8008 content: "\f186";
8009 }
8010 .fa-archive:before {
8011 content: "\f187";
8012 }
8013 .fa-bug:before {
8014 content: "\f188";
8015 }
8016 .fa-vk:before {
8017 content: "\f189";
8018 }
8019 .fa-weibo:before {
8020 content: "\f18a";
8021 }
8022 .fa-renren:before {
8023 content: "\f18b";
8024 }
8025 .fa-pagelines:before {
8026 content: "\f18c";
8027 }
8028 .fa-stack-exchange:before {
8029 content: "\f18d";
8030 }
8031 .fa-arrow-circle-o-right:before {
8032 content: "\f18e";
8033 }
8034 .fa-arrow-circle-o-left:before {
8035 content: "\f190";
8036 }
8037 .fa-toggle-left:before,
8038 .fa-caret-square-o-left:before {
8039 content: "\f191";
8040 }
8041 .fa-dot-circle-o:before {
8042 content: "\f192";
8043 }
8044 .fa-wheelchair:before {
8045 content: "\f193";
8046 }
8047 .fa-vimeo-square:before {
8048 content: "\f194";
8049 }
8050 .fa-turkish-lira:before,
8051 .fa-try:before {
8052 content: "\f195";
8053 }
8054 .fa-plus-square-o:before {
8055 content: "\f196";
8056 }
8057 .fa-space-shuttle:before {
8058 content: "\f197";
8059 }
8060 .fa-slack:before {
8061 content: "\f198";
8062 }
8063 .fa-envelope-square:before {
8064 content: "\f199";
8065 }
8066 .fa-wordpress:before {
8067 content: "\f19a";
8068 }
8069 .fa-openid:before {
8070 content: "\f19b";
8071 }
8072 .fa-institution:before,
8073 .fa-bank:before,
8074 .fa-university:before {
8075 content: "\f19c";
8076 }
8077 .fa-mortar-board:before,
8078 .fa-graduation-cap:before {
8079 content: "\f19d";
8080 }
8081 .fa-yahoo:before {
8082 content: "\f19e";
8083 }
8084 .fa-google:before {
8085 content: "\f1a0";
8086 }
8087 .fa-reddit:before {
8088 content: "\f1a1";
8089 }
8090 .fa-reddit-square:before {
8091 content: "\f1a2";
8092 }
8093 .fa-stumbleupon-circle:before {
8094 content: "\f1a3";
8095 }
8096 .fa-stumbleupon:before {
8097 content: "\f1a4";
8098 }
8099 .fa-delicious:before {
8100 content: "\f1a5";
8101 }
8102 .fa-digg:before {
8103 content: "\f1a6";
8104 }
8105 .fa-pied-piper:before {
8106 content: "\f1a7";
8107 }
8108 .fa-pied-piper-alt:before {
8109 content: "\f1a8";
8110 }
8111 .fa-drupal:before {
8112 content: "\f1a9";
8113 }
8114 .fa-joomla:before {
8115 content: "\f1aa";
8116 }
8117 .fa-language:before {
8118 content: "\f1ab";
8119 }
8120 .fa-fax:before {
8121 content: "\f1ac";
8122 }
8123 .fa-building:before {
8124 content: "\f1ad";
8125 }
8126 .fa-child:before {
8127 content: "\f1ae";
8128 }
8129 .fa-paw:before {
8130 content: "\f1b0";
8131 }
8132 .fa-spoon:before {
8133 content: "\f1b1";
8134 }
8135 .fa-cube:before {
8136 content: "\f1b2";
8137 }
8138 .fa-cubes:before {
8139 content: "\f1b3";
8140 }
8141 .fa-behance:before {
8142 content: "\f1b4";
8143 }
8144 .fa-behance-square:before {
8145 content: "\f1b5";
8146 }
8147 .fa-steam:before {
8148 content: "\f1b6";
8149 }
8150 .fa-steam-square:before {
8151 content: "\f1b7";
8152 }
8153 .fa-recycle:before {
8154 content: "\f1b8";
8155 }
8156 .fa-automobile:before,
8157 .fa-car:before {
8158 content: "\f1b9";
8159 }
8160 .fa-cab:before,
8161 .fa-taxi:before {
8162 content: "\f1ba";
8163 }
8164 .fa-tree:before {
8165 content: "\f1bb";
8166 }
8167 .fa-spotify:before {
8168 content: "\f1bc";
8169 }
8170 .fa-deviantart:before {
8171 content: "\f1bd";
8172 }
8173 .fa-soundcloud:before {
8174 content: "\f1be";
8175 }
8176 .fa-database:before {
8177 content: "\f1c0";
8178 }
8179 .fa-file-pdf-o:before {
8180 content: "\f1c1";
8181 }
8182 .fa-file-word-o:before {
8183 content: "\f1c2";
8184 }
8185 .fa-file-excel-o:before {
8186 content: "\f1c3";
8187 }
8188 .fa-file-powerpoint-o:before {
8189 content: "\f1c4";
8190 }
8191 .fa-file-photo-o:before,
8192 .fa-file-picture-o:before,
8193 .fa-file-image-o:before {
8194 content: "\f1c5";
8195 }
8196 .fa-file-zip-o:before,
8197 .fa-file-archive-o:before {
8198 content: "\f1c6";
8199 }
8200 .fa-file-sound-o:before,
8201 .fa-file-audio-o:before {
8202 content: "\f1c7";
8203 }
8204 .fa-file-movie-o:before,
8205 .fa-file-video-o:before {
8206 content: "\f1c8";
8207 }
8208 .fa-file-code-o:before {
8209 content: "\f1c9";
8210 }
8211 .fa-vine:before {
8212 content: "\f1ca";
8213 }
8214 .fa-codepen:before {
8215 content: "\f1cb";
8216 }
8217 .fa-jsfiddle:before {
8218 content: "\f1cc";
8219 }
8220 .fa-life-bouy:before,
8221 .fa-life-buoy:before,
8222 .fa-life-saver:before,
8223 .fa-support:before,
8224 .fa-life-ring:before {
8225 content: "\f1cd";
8226 }
8227 .fa-circle-o-notch:before {
8228 content: "\f1ce";
8229 }
8230 .fa-ra:before,
8231 .fa-rebel:before {
8232 content: "\f1d0";
8233 }
8234 .fa-ge:before,
8235 .fa-empire:before {
8236 content: "\f1d1";
8237 }
8238 .fa-git-square:before {
8239 content: "\f1d2";
8240 }
8241 .fa-git:before {
8242 content: "\f1d3";
8243 }
8244 .fa-hacker-news:before {
8245 content: "\f1d4";
8246 }
8247 .fa-tencent-weibo:before {
8248 content: "\f1d5";
8249 }
8250 .fa-qq:before {
8251 content: "\f1d6";
8252 }
8253 .fa-wechat:before,
8254 .fa-weixin:before {
8255 content: "\f1d7";
8256 }
8257 .fa-send:before,
8258 .fa-paper-plane:before {
8259 content: "\f1d8";
8260 }
8261 .fa-send-o:before,
8262 .fa-paper-plane-o:before {
8263 content: "\f1d9";
8264 }
8265 .fa-history:before {
8266 content: "\f1da";
8267 }
8268 .fa-circle-thin:before {
8269 content: "\f1db";
8270 }
8271 .fa-header:before {
8272 content: "\f1dc";
8273 }
8274 .fa-paragraph:before {
8275 content: "\f1dd";
8276 }
8277 .fa-sliders:before {
8278 content: "\f1de";
8279 }
8280 .fa-share-alt:before {
8281 content: "\f1e0";
8282 }
8283 .fa-share-alt-square:before {
8284 content: "\f1e1";
8285 }
8286 .fa-bomb:before {
8287 content: "\f1e2";
8288 }
8289 .fa-soccer-ball-o:before,
8290 .fa-futbol-o:before {
8291 content: "\f1e3";
8292 }
8293 .fa-tty:before {
8294 content: "\f1e4";
8295 }
8296 .fa-binoculars:before {
8297 content: "\f1e5";
8298 }
8299 .fa-plug:before {
8300 content: "\f1e6";
8301 }
8302 .fa-slideshare:before {
8303 content: "\f1e7";
8304 }
8305 .fa-twitch:before {
8306 content: "\f1e8";
8307 }
8308 .fa-yelp:before {
8309 content: "\f1e9";
8310 }
8311 .fa-newspaper-o:before {
8312 content: "\f1ea";
8313 }
8314 .fa-wifi:before {
8315 content: "\f1eb";
8316 }
8317 .fa-calculator:before {
8318 content: "\f1ec";
8319 }
8320 .fa-paypal:before {
8321 content: "\f1ed";
8322 }
8323 .fa-google-wallet:before {
8324 content: "\f1ee";
8325 }
8326 .fa-cc-visa:before {
8327 content: "\f1f0";
8328 }
8329 .fa-cc-mastercard:before {
8330 content: "\f1f1";
8331 }
8332 .fa-cc-discover:before {
8333 content: "\f1f2";
8334 }
8335 .fa-cc-amex:before {
8336 content: "\f1f3";
8337 }
8338 .fa-cc-paypal:before {
8339 content: "\f1f4";
8340 }
8341 .fa-cc-stripe:before {
8342 content: "\f1f5";
8343 }
8344 .fa-bell-slash:before {
8345 content: "\f1f6";
8346 }
8347 .fa-bell-slash-o:before {
8348 content: "\f1f7";
8349 }
8350 .fa-trash:before {
8351 content: "\f1f8";
8352 }
8353 .fa-copyright:before {
8354 content: "\f1f9";
8355 }
8356 .fa-at:before {
8357 content: "\f1fa";
8358 }
8359 .fa-eyedropper:before {
8360 content: "\f1fb";
8361 }
8362 .fa-paint-brush:before {
8363 content: "\f1fc";
8364 }
8365 .fa-birthday-cake:before {
8366 content: "\f1fd";
8367 }
8368 .fa-area-chart:before {
8369 content: "\f1fe";
8370 }
8371 .fa-pie-chart:before {
8372 content: "\f200";
8373 }
8374 .fa-line-chart:before {
8375 content: "\f201";
8376 }
8377 .fa-lastfm:before {
8378 content: "\f202";
8379 }
8380 .fa-lastfm-square:before {
8381 content: "\f203";
8382 }
8383 .fa-toggle-off:before {
8384 content: "\f204";
8385 }
8386 .fa-toggle-on:before {
8387 content: "\f205";
8388 }
8389 .fa-bicycle:before {
8390 content: "\f206";
8391 }
8392 .fa-bus:before {
8393 content: "\f207";
8394 }
8395 .fa-ioxhost:before {
8396 content: "\f208";
8397 }
8398 .fa-angellist:before {
8399 content: "\f209";
8400 }
8401 .fa-cc:before {
8402 content: "\f20a";
8403 }
8404 .fa-shekel:before,
8405 .fa-sheqel:before,
8406 .fa-ils:before {
8407 content: "\f20b";
8408 }
8409 .fa-meanpath:before {
8410 content: "\f20c";
8411 }
8412 /*!
8413 *
8414 * IPython base
8415 *
8416 */
8417 .modal.fade .modal-dialog {
8418 -webkit-transform: translate(0, 0);
8419 -ms-transform: translate(0, 0);
8420 -o-transform: translate(0, 0);
8421 transform: translate(0, 0);
8422 }
8423 code {
8424 color: #000;
8425 }
8426 pre {
8427 font-size: inherit;
8428 line-height: inherit;
8429 }
8430 label {
8431 font-weight: normal;
8432 }
8433 /* Make the page background atleast 100% the height of the view port */
8434 /* Make the page itself atleast 70% the height of the view port */
8435 .border-box-sizing {
8436 box-sizing: border-box;
8437 -moz-box-sizing: border-box;
8438 -webkit-box-sizing: border-box;
8439 }
8440 .corner-all {
8441 border-radius: 2px;
8442 }
8443 .no-padding {
8444 padding: 0px;
8445 }
8446 /* Flexible box model classes */
8447 /* Taken from Alex Russell http://infrequently.org/2009/08/css-3-progress/ */
8448 /* This file is a compatability layer. It allows the usage of flexible box
8449 model layouts accross multiple browsers, including older browsers. The newest,
8450 universal implementation of the flexible box model is used when available (see
8451 `Modern browsers` comments below). Browsers that are known to implement this
8452 new spec completely include:
8453
8454 Firefox 28.0+
8455 Chrome 29.0+
8456 Internet Explorer 11+
8457 Opera 17.0+
8458
8459 Browsers not listed, including Safari, are supported via the styling under the
8460 `Old browsers` comments below.
8461 */
8462 .hbox {
8463 /* Old browsers */
8464 display: -webkit-box;
8465 -webkit-box-orient: horizontal;
8466 -webkit-box-align: stretch;
8467 display: -moz-box;
8468 -moz-box-orient: horizontal;
8469 -moz-box-align: stretch;
8470 display: box;
8471 box-orient: horizontal;
8472 box-align: stretch;
8473 /* Modern browsers */
8474 display: flex;
8475 flex-direction: row;
8476 align-items: stretch;
8477 }
8478 .hbox > * {
8479 /* Old browsers */
8480 -webkit-box-flex: 0;
8481 -moz-box-flex: 0;
8482 box-flex: 0;
8483 /* Modern browsers */
8484 flex: none;
8485 }
8486 .vbox {
8487 /* Old browsers */
8488 display: -webkit-box;
8489 -webkit-box-orient: vertical;
8490 -webkit-box-align: stretch;
8491 display: -moz-box;
8492 -moz-box-orient: vertical;
8493 -moz-box-align: stretch;
8494 display: box;
8495 box-orient: vertical;
8496 box-align: stretch;
8497 /* Modern browsers */
8498 display: flex;
8499 flex-direction: column;
8500 align-items: stretch;
8501 }
8502 .vbox > * {
8503 /* Old browsers */
8504 -webkit-box-flex: 0;
8505 -moz-box-flex: 0;
8506 box-flex: 0;
8507 /* Modern browsers */
8508 flex: none;
8509 }
8510 .hbox.reverse,
8511 .vbox.reverse,
8512 .reverse {
8513 /* Old browsers */
8514 -webkit-box-direction: reverse;
8515 -moz-box-direction: reverse;
8516 box-direction: reverse;
8517 /* Modern browsers */
8518 flex-direction: row-reverse;
8519 }
8520 .hbox.box-flex0,
8521 .vbox.box-flex0,
8522 .box-flex0 {
8523 /* Old browsers */
8524 -webkit-box-flex: 0;
8525 -moz-box-flex: 0;
8526 box-flex: 0;
8527 /* Modern browsers */
8528 flex: none;
8529 width: auto;
8530 }
8531 .hbox.box-flex1,
8532 .vbox.box-flex1,
8533 .box-flex1 {
8534 /* Old browsers */
8535 -webkit-box-flex: 1;
8536 -moz-box-flex: 1;
8537 box-flex: 1;
8538 /* Modern browsers */
8539 flex: 1;
8540 }
8541 .hbox.box-flex,
8542 .vbox.box-flex,
8543 .box-flex {
8544 /* Old browsers */
8545 /* Old browsers */
8546 -webkit-box-flex: 1;
8547 -moz-box-flex: 1;
8548 box-flex: 1;
8549 /* Modern browsers */
8550 flex: 1;
8551 }
8552 .hbox.box-flex2,
8553 .vbox.box-flex2,
8554 .box-flex2 {
8555 /* Old browsers */
8556 -webkit-box-flex: 2;
8557 -moz-box-flex: 2;
8558 box-flex: 2;
8559 /* Modern browsers */
8560 flex: 2;
8561 }
8562 .box-group1 {
8563 /* Deprecated */
8564 -webkit-box-flex-group: 1;
8565 -moz-box-flex-group: 1;
8566 box-flex-group: 1;
8567 }
8568 .box-group2 {
8569 /* Deprecated */
8570 -webkit-box-flex-group: 2;
8571 -moz-box-flex-group: 2;
8572 box-flex-group: 2;
8573 }
8574 .hbox.start,
8575 .vbox.start,
8576 .start {
8577 /* Old browsers */
8578 -webkit-box-pack: start;
8579 -moz-box-pack: start;
8580 box-pack: start;
8581 /* Modern browsers */
8582 justify-content: flex-start;
8583 }
8584 .hbox.end,
8585 .vbox.end,
8586 .end {
8587 /* Old browsers */
8588 -webkit-box-pack: end;
8589 -moz-box-pack: end;
8590 box-pack: end;
8591 /* Modern browsers */
8592 justify-content: flex-end;
8593 }
8594 .hbox.center,
8595 .vbox.center,
8596 .center {
8597 /* Old browsers */
8598 -webkit-box-pack: center;
8599 -moz-box-pack: center;
8600 box-pack: center;
8601 /* Modern browsers */
8602 justify-content: center;
8603 }
8604 .hbox.baseline,
8605 .vbox.baseline,
8606 .baseline {
8607 /* Old browsers */
8608 -webkit-box-pack: baseline;
8609 -moz-box-pack: baseline;
8610 box-pack: baseline;
8611 /* Modern browsers */
8612 justify-content: baseline;
8613 }
8614 .hbox.stretch,
8615 .vbox.stretch,
8616 .stretch {
8617 /* Old browsers */
8618 -webkit-box-pack: stretch;
8619 -moz-box-pack: stretch;
8620 box-pack: stretch;
8621 /* Modern browsers */
8622 justify-content: stretch;
8623 }
8624 .hbox.align-start,
8625 .vbox.align-start,
8626 .align-start {
8627 /* Old browsers */
8628 -webkit-box-align: start;
8629 -moz-box-align: start;
8630 box-align: start;
8631 /* Modern browsers */
8632 align-items: flex-start;
8633 }
8634 .hbox.align-end,
8635 .vbox.align-end,
8636 .align-end {
8637 /* Old browsers */
8638 -webkit-box-align: end;
8639 -moz-box-align: end;
8640 box-align: end;
8641 /* Modern browsers */
8642 align-items: flex-end;
8643 }
8644 .hbox.align-center,
8645 .vbox.align-center,
8646 .align-center {
8647 /* Old browsers */
8648 -webkit-box-align: center;
8649 -moz-box-align: center;
8650 box-align: center;
8651 /* Modern browsers */
8652 align-items: center;
8653 }
8654 .hbox.align-baseline,
8655 .vbox.align-baseline,
8656 .align-baseline {
8657 /* Old browsers */
8658 -webkit-box-align: baseline;
8659 -moz-box-align: baseline;
8660 box-align: baseline;
8661 /* Modern browsers */
8662 align-items: baseline;
8663 }
8664 .hbox.align-stretch,
8665 .vbox.align-stretch,
8666 .align-stretch {
8667 /* Old browsers */
8668 -webkit-box-align: stretch;
8669 -moz-box-align: stretch;
8670 box-align: stretch;
8671 /* Modern browsers */
8672 align-items: stretch;
8673 }
8674 div.error {
8675 margin: 2em;
8676 text-align: center;
8677 }
8678 div.error > h1 {
8679 font-size: 500%;
8680 line-height: normal;
8681 }
8682 div.error > p {
8683 font-size: 200%;
8684 line-height: normal;
8685 }
8686 div.traceback-wrapper {
8687 text-align: left;
8688 max-width: 800px;
8689 margin: auto;
8690 }
8691 /**
8692 * Primary styles
8693 *
8694 * Author: Jupyter Development Team
8695 */
8696 body {
8697 background-color: #fff;
8698 /* This makes sure that the body covers the entire window and needs to
8699 be in a different element than the display: box in wrapper below */
8700 position: absolute;
8701 left: 0px;
8702 right: 0px;
8703 top: 0px;
8704 bottom: 0px;
8705 overflow: visible;
8706 }
8707 body > #header {
8708 /* Initially hidden to prevent FLOUC */
8709 display: none;
8710 background-color: #fff;
8711 /* Display over codemirror */
8712 position: relative;
8713 z-index: 100;
8714 }
8715 body > #header #header-container {
8716 padding-bottom: 5px;
8717 padding-top: 5px;
8718 box-sizing: border-box;
8719 -moz-box-sizing: border-box;
8720 -webkit-box-sizing: border-box;
8721 }
8722 body > #header .header-bar {
8723 width: 100%;
8724 height: 1px;
8725 background: #e7e7e7;
8726 margin-bottom: -1px;
8727 }
8728 @media print {
8729 body > #header {
8730 display: none !important;
8731 }
8732 }
8733 #header-spacer {
8734 width: 100%;
8735 visibility: hidden;
8736 }
8737 @media print {
8738 #header-spacer {
8739 display: none;
8740 }
8741 }
8742 #ipython_notebook {
8743 padding-left: 0px;
8744 padding-top: 1px;
8745 padding-bottom: 1px;
8746 }
8747 @media (max-width: 991px) {
8748 #ipython_notebook {
8749 margin-left: 10px;
8750 }
8751 }
8752 [dir="rtl"] #ipython_notebook {
8753 float: right !important;
8754 }
8755 #noscript {
8756 width: auto;
8757 padding-top: 16px;
8758 padding-bottom: 16px;
8759 text-align: center;
8760 font-size: 22px;
8761 color: red;
8762 font-weight: bold;
8763 }
8764 #ipython_notebook img {
8765 height: 28px;
8766 }
8767 #site {
8768 width: 100%;
8769 display: none;
8770 box-sizing: border-box;
8771 -moz-box-sizing: border-box;
8772 -webkit-box-sizing: border-box;
8773 overflow: auto;
8774 }
8775 @media print {
8776 #site {
8777 height: auto !important;
8778 }
8779 }
8780 /* Smaller buttons */
8781 .ui-button .ui-button-text {
8782 padding: 0.2em 0.8em;
8783 font-size: 77%;
8784 }
8785 input.ui-button {
8786 padding: 0.3em 0.9em;
8787 }
8788 span#login_widget {
8789 float: right;
8790 }
8791 span#login_widget > .button,
8792 #logout {
8793 color: #333;
8794 background-color: #fff;
8795 border-color: #ccc;
8796 }
8797 span#login_widget > .button:focus,
8798 #logout:focus,
8799 span#login_widget > .button.focus,
8800 #logout.focus {
8801 color: #333;
8802 background-color: #e6e6e6;
8803 border-color: #8c8c8c;
8804 }
8805 span#login_widget > .button:hover,
8806 #logout:hover {
8807 color: #333;
8808 background-color: #e6e6e6;
8809 border-color: #adadad;
8810 }
8811 span#login_widget > .button:active,
8812 #logout:active,
8813 span#login_widget > .button.active,
8814 #logout.active,
8815 .open > .dropdown-togglespan#login_widget > .button,
8816 .open > .dropdown-toggle#logout {
8817 color: #333;
8818 background-color: #e6e6e6;
8819 border-color: #adadad;
8820 }
8821 span#login_widget > .button:active:hover,
8822 #logout:active:hover,
8823 span#login_widget > .button.active:hover,
8824 #logout.active:hover,
8825 .open > .dropdown-togglespan#login_widget > .button:hover,
8826 .open > .dropdown-toggle#logout:hover,
8827 span#login_widget > .button:active:focus,
8828 #logout:active:focus,
8829 span#login_widget > .button.active:focus,
8830 #logout.active:focus,
8831 .open > .dropdown-togglespan#login_widget > .button:focus,
8832 .open > .dropdown-toggle#logout:focus,
8833 span#login_widget > .button:active.focus,
8834 #logout:active.focus,
8835 span#login_widget > .button.active.focus,
8836 #logout.active.focus,
8837 .open > .dropdown-togglespan#login_widget > .button.focus,
8838 .open > .dropdown-toggle#logout.focus {
8839 color: #333;
8840 background-color: #d4d4d4;
8841 border-color: #8c8c8c;
8842 }
8843 span#login_widget > .button:active,
8844 #logout:active,
8845 span#login_widget > .button.active,
8846 #logout.active,
8847 .open > .dropdown-togglespan#login_widget > .button,
8848 .open > .dropdown-toggle#logout {
8849 background-image: none;
8850 }
8851 span#login_widget > .button.disabled:hover,
8852 #logout.disabled:hover,
8853 span#login_widget > .button[disabled]:hover,
8854 #logout[disabled]:hover,
8855 fieldset[disabled] span#login_widget > .button:hover,
8856 fieldset[disabled] #logout:hover,
8857 span#login_widget > .button.disabled:focus,
8858 #logout.disabled:focus,
8859 span#login_widget > .button[disabled]:focus,
8860 #logout[disabled]:focus,
8861 fieldset[disabled] span#login_widget > .button:focus,
8862 fieldset[disabled] #logout:focus,
8863 span#login_widget > .button.disabled.focus,
8864 #logout.disabled.focus,
8865 span#login_widget > .button[disabled].focus,
8866 #logout[disabled].focus,
8867 fieldset[disabled] span#login_widget > .button.focus,
8868 fieldset[disabled] #logout.focus {
8869 background-color: #fff;
8870 border-color: #ccc;
8871 }
8872 span#login_widget > .button .badge,
8873 #logout .badge {
8874 color: #fff;
8875 background-color: #333;
8876 }
8877 .nav-header {
8878 text-transform: none;
8879 }
8880 #header > span {
8881 margin-top: 10px;
8882 }
8883 .modal_stretch .modal-dialog {
8884 /* Old browsers */
8885 display: -webkit-box;
8886 -webkit-box-orient: vertical;
8887 -webkit-box-align: stretch;
8888 display: -moz-box;
8889 -moz-box-orient: vertical;
8890 -moz-box-align: stretch;
8891 display: box;
8892 box-orient: vertical;
8893 box-align: stretch;
8894 /* Modern browsers */
8895 display: flex;
8896 flex-direction: column;
8897 align-items: stretch;
8898 min-height: 80vh;
8899 }
8900 .modal_stretch .modal-dialog .modal-body {
8901 max-height: calc(100vh - 200px);
8902 overflow: auto;
8903 flex: 1;
8904 }
8905 @media (min-width: 768px) {
8906 .modal .modal-dialog {
8907 width: 700px;
8908 }
8909 }
8910 @media (min-width: 768px) {
8911 select.form-control {
8912 margin-left: 12px;
8913 margin-right: 12px;
8914 }
8915 }
8916 /*!
8917 *
8918 * IPython auth
8919 *
8920 */
8921 .center-nav {
8922 display: inline-block;
8923 margin-bottom: -4px;
8924 }
8925 /*!
8926 *
8927 * IPython tree view
8928 *
8929 */
8930 /* We need an invisible input field on top of the sentense*/
8931 /* "Drag file onto the list ..." */
8932 .alternate_upload {
8933 background-color: none;
8934 display: inline;
8935 }
8936 .alternate_upload.form {
8937 padding: 0;
8938 margin: 0;
8939 }
8940 .alternate_upload input.fileinput {
8941 text-align: center;
8942 vertical-align: middle;
8943 display: inline;
8944 opacity: 0;
8945 z-index: 2;
8946 width: 12ex;
8947 margin-right: -12ex;
8948 }
8949 .alternate_upload .btn-upload {
8950 height: 22px;
8951 }
8952 /**
8953 * Primary styles
8954 *
8955 * Author: Jupyter Development Team
8956 */
8957 [dir="rtl"] #tabs li {
8958 float: right;
8959 }
8960 ul#tabs {
8961 margin-bottom: 4px;
8962 }
8963 [dir="rtl"] ul#tabs {
8964 margin-right: 0px;
8965 }
8966 ul#tabs a {
8967 padding-top: 6px;
8968 padding-bottom: 4px;
8969 }
8970 ul.breadcrumb a:focus,
8971 ul.breadcrumb a:hover {
8972 text-decoration: none;
8973 }
8974 ul.breadcrumb i.icon-home {
8975 font-size: 16px;
8976 margin-right: 4px;
8977 }
8978 ul.breadcrumb span {
8979 color: #5e5e5e;
8980 }
8981 .list_toolbar {
8982 padding: 4px 0 4px 0;
8983 vertical-align: middle;
8984 }
8985 .list_toolbar .tree-buttons {
8986 padding-top: 1px;
8987 }
8988 [dir="rtl"] .list_toolbar .tree-buttons {
8989 float: left !important;
8990 }
8991 [dir="rtl"] .list_toolbar .pull-right {
8992 padding-top: 1px;
8993 float: left !important;
8994 }
8995 [dir="rtl"] .list_toolbar .pull-left {
8996 float: right !important;
8997 }
8998 .dynamic-buttons {
8999 padding-top: 3px;
9000 display: inline-block;
9001 }
9002 .list_toolbar [class*="span"] {
9003 min-height: 24px;
9004 }
9005 .list_header {
9006 font-weight: bold;
9007 background-color: #EEE;
9008 }
9009 .list_placeholder {
9010 font-weight: bold;
9011 padding-top: 4px;
9012 padding-bottom: 4px;
9013 padding-left: 7px;
9014 padding-right: 7px;
9015 }
9016 .list_container {
9017 margin-top: 4px;
9018 margin-bottom: 20px;
9019 border: 1px solid #ddd;
9020 border-radius: 2px;
9021 }
9022 .list_container > div {
9023 border-bottom: 1px solid #ddd;
9024 }
9025 .list_container > div:hover .list-item {
9026 background-color: red;
9027 }
9028 .list_container > div:last-child {
9029 border: none;
9030 }
9031 .list_item:hover .list_item {
9032 background-color: #ddd;
9033 }
9034 .list_item a {
9035 text-decoration: none;
9036 }
9037 .list_item:hover {
9038 background-color: #fafafa;
9039 }
9040 .list_header > div,
9041 .list_item > div {
9042 padding-top: 4px;
9043 padding-bottom: 4px;
9044 padding-left: 7px;
9045 padding-right: 7px;
9046 line-height: 22px;
9047 }
9048 .list_header > div input,
9049 .list_item > div input {
9050 margin-right: 7px;
9051 margin-left: 14px;
9052 vertical-align: baseline;
9053 line-height: 22px;
9054 position: relative;
9055 top: -1px;
9056 }
9057 .list_header > div .item_link,
9058 .list_item > div .item_link {
9059 margin-left: -1px;
9060 vertical-align: baseline;
9061 line-height: 22px;
9062 }
9063 .new-file input[type=checkbox] {
9064 visibility: hidden;
9065 }
9066 .item_name {
9067 line-height: 22px;
9068 height: 24px;
9069 }
9070 .item_icon {
9071 font-size: 14px;
9072 color: #5e5e5e;
9073 margin-right: 7px;
9074 margin-left: 7px;
9075 line-height: 22px;
9076 vertical-align: baseline;
9077 }
9078 .item_buttons {
9079 line-height: 1em;
9080 margin-left: -5px;
9081 }
9082 .item_buttons .btn,
9083 .item_buttons .btn-group,
9084 .item_buttons .input-group {
9085 float: left;
9086 }
9087 .item_buttons > .btn,
9088 .item_buttons > .btn-group,
9089 .item_buttons > .input-group {
9090 margin-left: 5px;
9091 }
9092 .item_buttons .btn {
9093 min-width: 13ex;
9094 }
9095 .item_buttons .running-indicator {
9096 padding-top: 4px;
9097 color: #5cb85c;
9098 }
9099 .item_buttons .kernel-name {
9100 padding-top: 4px;
9101 color: #5bc0de;
9102 margin-right: 7px;
9103 float: left;
9104 }
9105 .toolbar_info {
9106 height: 24px;
9107 line-height: 24px;
9108 }
9109 .list_item input:not([type=checkbox]) {
9110 padding-top: 3px;
9111 padding-bottom: 3px;
9112 height: 22px;
9113 line-height: 14px;
9114 margin: 0px;
9115 }
9116 .highlight_text {
9117 color: blue;
9118 }
9119 #project_name {
9120 display: inline-block;
9121 padding-left: 7px;
9122 margin-left: -2px;
9123 }
9124 #project_name > .breadcrumb {
9125 padding: 0px;
9126 margin-bottom: 0px;
9127 background-color: transparent;
9128 font-weight: bold;
9129 }
9130 #tree-selector {
9131 padding-right: 0px;
9132 }
9133 [dir="rtl"] #tree-selector a {
9134 float: right;
9135 }
9136 #button-select-all {
9137 min-width: 50px;
9138 }
9139 #select-all {
9140 margin-left: 7px;
9141 margin-right: 2px;
9142 }
9143 .menu_icon {
9144 margin-right: 2px;
9145 }
9146 .tab-content .row {
9147 margin-left: 0px;
9148 margin-right: 0px;
9149 }
9150 .folder_icon:before {
9151 display: inline-block;
9152 font: normal normal normal 14px/1 FontAwesome;
9153 font-size: inherit;
9154 text-rendering: auto;
9155 -webkit-font-smoothing: antialiased;
9156 -moz-osx-font-smoothing: grayscale;
9157 content: "\f114";
9158 }
9159 .folder_icon:before.pull-left {
9160 margin-right: .3em;
9161 }
9162 .folder_icon:before.pull-right {
9163 margin-left: .3em;
9164 }
9165 .notebook_icon:before {
9166 display: inline-block;
9167 font: normal normal normal 14px/1 FontAwesome;
9168 font-size: inherit;
9169 text-rendering: auto;
9170 -webkit-font-smoothing: antialiased;
9171 -moz-osx-font-smoothing: grayscale;
9172 content: "\f02d";
9173 position: relative;
9174 top: -1px;
9175 }
9176 .notebook_icon:before.pull-left {
9177 margin-right: .3em;
9178 }
9179 .notebook_icon:before.pull-right {
9180 margin-left: .3em;
9181 }
9182 .running_notebook_icon:before {
9183 display: inline-block;
9184 font: normal normal normal 14px/1 FontAwesome;
9185 font-size: inherit;
9186 text-rendering: auto;
9187 -webkit-font-smoothing: antialiased;
9188 -moz-osx-font-smoothing: grayscale;
9189 content: "\f02d";
9190 position: relative;
9191 top: -1px;
9192 color: #5cb85c;
9193 }
9194 .running_notebook_icon:before.pull-left {
9195 margin-right: .3em;
9196 }
9197 .running_notebook_icon:before.pull-right {
9198 margin-left: .3em;
9199 }
9200 .file_icon:before {
9201 display: inline-block;
9202 font: normal normal normal 14px/1 FontAwesome;
9203 font-size: inherit;
9204 text-rendering: auto;
9205 -webkit-font-smoothing: antialiased;
9206 -moz-osx-font-smoothing: grayscale;
9207 content: "\f016";
9208 position: relative;
9209 top: -2px;
9210 }
9211 .file_icon:before.pull-left {
9212 margin-right: .3em;
9213 }
9214 .file_icon:before.pull-right {
9215 margin-left: .3em;
9216 }
9217 #notebook_toolbar .pull-right {
9218 padding-top: 0px;
9219 margin-right: -1px;
9220 }
9221 ul#new-menu {
9222 left: auto;
9223 right: 0;
9224 }
9225 [dir="rtl"] #new-menu {
9226 text-align: right;
9227 }
9228 .kernel-menu-icon {
9229 padding-right: 12px;
9230 width: 24px;
9231 content: "\f096";
9232 }
9233 .kernel-menu-icon:before {
9234 content: "\f096";
9235 }
9236 .kernel-menu-icon-current:before {
9237 content: "\f00c";
9238 }
9239 #tab_content {
9240 padding-top: 20px;
9241 }
9242 #running .panel-group .panel {
9243 margin-top: 3px;
9244 margin-bottom: 1em;
9245 }
9246 #running .panel-group .panel .panel-heading {
9247 background-color: #EEE;
9248 padding-top: 4px;
9249 padding-bottom: 4px;
9250 padding-left: 7px;
9251 padding-right: 7px;
9252 line-height: 22px;
9253 }
9254 #running .panel-group .panel .panel-heading a:focus,
9255 #running .panel-group .panel .panel-heading a:hover {
9256 text-decoration: none;
9257 }
9258 #running .panel-group .panel .panel-body {
9259 padding: 0px;
9260 }
9261 #running .panel-group .panel .panel-body .list_container {
9262 margin-top: 0px;
9263 margin-bottom: 0px;
9264 border: 0px;
9265 border-radius: 0px;
9266 }
9267 #running .panel-group .panel .panel-body .list_container .list_item {
9268 border-bottom: 1px solid #ddd;
9269 }
9270 #running .panel-group .panel .panel-body .list_container .list_item:last-child {
9271 border-bottom: 0px;
9272 }
9273 [dir="rtl"] #running .col-sm-8 {
9274 float: right !important;
9275 }
9276 .delete-button {
9277 display: none;
9278 }
9279 .duplicate-button {
9280 display: none;
9281 }
9282 .rename-button {
9283 display: none;
9284 }
9285 .shutdown-button {
9286 display: none;
9287 }
9288 .dynamic-instructions {
9289 display: inline-block;
9290 padding-top: 4px;
9291 }
9292 /*!
9293 *
9294 * IPython text editor webapp
9295 *
9296 */
9297 .selected-keymap i.fa {
9298 padding: 0px 5px;
9299 }
9300 .selected-keymap i.fa:before {
9301 content: "\f00c";
9302 }
9303 #mode-menu {
9304 overflow: auto;
9305 max-height: 20em;
9306 }
9307 .edit_app #header {
9308 -webkit-box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
9309 box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
9310 }
9311 .edit_app #menubar .navbar {
9312 /* Use a negative 1 bottom margin, so the border overlaps the border of the
9313 header */
9314 margin-bottom: -1px;
9315 }
9316 .dirty-indicator {
9317 display: inline-block;
9318 font: normal normal normal 14px/1 FontAwesome;
9319 font-size: inherit;
9320 text-rendering: auto;
9321 -webkit-font-smoothing: antialiased;
9322 -moz-osx-font-smoothing: grayscale;
9323 width: 20px;
9324 }
9325 .dirty-indicator.pull-left {
9326 margin-right: .3em;
9327 }
9328 .dirty-indicator.pull-right {
9329 margin-left: .3em;
9330 }
9331 .dirty-indicator-dirty {
9332 display: inline-block;
9333 font: normal normal normal 14px/1 FontAwesome;
9334 font-size: inherit;
9335 text-rendering: auto;
9336 -webkit-font-smoothing: antialiased;
9337 -moz-osx-font-smoothing: grayscale;
9338 width: 20px;
9339 }
9340 .dirty-indicator-dirty.pull-left {
9341 margin-right: .3em;
9342 }
9343 .dirty-indicator-dirty.pull-right {
9344 margin-left: .3em;
9345 }
9346 .dirty-indicator-clean {
9347 display: inline-block;
9348 font: normal normal normal 14px/1 FontAwesome;
9349 font-size: inherit;
9350 text-rendering: auto;
9351 -webkit-font-smoothing: antialiased;
9352 -moz-osx-font-smoothing: grayscale;
9353 width: 20px;
9354 }
9355 .dirty-indicator-clean.pull-left {
9356 margin-right: .3em;
9357 }
9358 .dirty-indicator-clean.pull-right {
9359 margin-left: .3em;
9360 }
9361 .dirty-indicator-clean:before {
9362 display: inline-block;
9363 font: normal normal normal 14px/1 FontAwesome;
9364 font-size: inherit;
9365 text-rendering: auto;
9366 -webkit-font-smoothing: antialiased;
9367 -moz-osx-font-smoothing: grayscale;
9368 content: "\f00c";
9369 }
9370 .dirty-indicator-clean:before.pull-left {
9371 margin-right: .3em;
9372 }
9373 .dirty-indicator-clean:before.pull-right {
9374 margin-left: .3em;
9375 }
9376 #filename {
9377 font-size: 16pt;
9378 display: table;
9379 padding: 0px 5px;
9380 }
9381 #current-mode {
9382 padding-left: 5px;
9383 padding-right: 5px;
9384 }
9385 #texteditor-backdrop {
9386 padding-top: 20px;
9387 padding-bottom: 20px;
9388 }
9389 @media not print {
9390 #texteditor-backdrop {
9391 background-color: #EEE;
9392 }
9393 }
9394 @media print {
9395 #texteditor-backdrop #texteditor-container .CodeMirror-gutter,
9396 #texteditor-backdrop #texteditor-container .CodeMirror-gutters {
9397 background-color: #fff;
9398 }
9399 }
9400 @media not print {
9401 #texteditor-backdrop #texteditor-container .CodeMirror-gutter,
9402 #texteditor-backdrop #texteditor-container .CodeMirror-gutters {
9403 background-color: #fff;
9404 }
9405 }
9406 @media not print {
9407 #texteditor-backdrop #texteditor-container {
9408 padding: 0px;
9409 background-color: #fff;
9410 -webkit-box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
9411 box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
9412 }
9413 }
9414 /*!
9415 *
9416 * IPython notebook
9417 *
9418 */
9419 /* CSS font colors for translated ANSI colors. */
9420 .ansibold {
9421 font-weight: bold;
9422 }
9423 /* use dark versions for foreground, to improve visibility */
9424 .ansiblack {
9425 color: black;
9426 }
9427 .ansired {
9428 color: darkred;
9429 }
9430 .ansigreen {
9431 color: darkgreen;
9432 }
9433 .ansiyellow {
9434 color: #c4a000;
9435 }
9436 .ansiblue {
9437 color: darkblue;
9438 }
9439 .ansipurple {
9440 color: darkviolet;
9441 }
9442 .ansicyan {
9443 color: steelblue;
9444 }
9445 .ansigray {
9446 color: gray;
9447 }
9448 /* and light for background, for the same reason */
9449 .ansibgblack {
9450 background-color: black;
9451 }
9452 .ansibgred {
9453 background-color: red;
9454 }
9455 .ansibggreen {
9456 background-color: green;
9457 }
9458 .ansibgyellow {
9459 background-color: yellow;
9460 }
9461 .ansibgblue {
9462 background-color: blue;
9463 }
9464 .ansibgpurple {
9465 background-color: magenta;
9466 }
9467 .ansibgcyan {
9468 background-color: cyan;
9469 }
9470 .ansibggray {
9471 background-color: gray;
9472 }
9473 div.cell {
9474 /* Old browsers */
9475 display: -webkit-box;
9476 -webkit-box-orient: vertical;
9477 -webkit-box-align: stretch;
9478 display: -moz-box;
9479 -moz-box-orient: vertical;
9480 -moz-box-align: stretch;
9481 display: box;
9482 box-orient: vertical;
9483 box-align: stretch;
9484 /* Modern browsers */
9485 display: flex;
9486 flex-direction: column;
9487 align-items: stretch;
9488 border-radius: 2px;
9489 box-sizing: border-box;
9490 -moz-box-sizing: border-box;
9491 -webkit-box-sizing: border-box;
9492 border-width: 1px;
9493 border-style: solid;
9494 border-color: transparent;
9495 width: 100%;
9496 padding: 5px;
9497 /* This acts as a spacer between cells, that is outside the border */
9498 margin: 0px;
9499 outline: none;
9500 border-left-width: 1px;
9501 padding-left: 5px;
9502 background: linear-gradient(to right, transparent -40px, transparent 1px, transparent 1px, transparent 100%);
9503 }
9504 div.cell.jupyter-soft-selected {
9505 border-left-color: #90CAF9;
9506 border-left-color: #E3F2FD;
9507 border-left-width: 1px;
9508 padding-left: 5px;
9509 border-right-color: #E3F2FD;
9510 border-right-width: 1px;
9511 background: #E3F2FD;
9512 }
9513 @media print {
9514 div.cell.jupyter-soft-selected {
9515 border-color: transparent;
9516 }
9517 }
9518 div.cell.selected {
9519 border-color: #ababab;
9520 border-left-width: 0px;
9521 padding-left: 6px;
9522 background: linear-gradient(to right, #42A5F5 -40px, #42A5F5 5px, transparent 5px, transparent 100%);
9523 }
9524 @media print {
9525 div.cell.selected {
9526 border-color: transparent;
9527 }
9528 }
9529 div.cell.selected.jupyter-soft-selected {
9530 border-left-width: 0;
9531 padding-left: 6px;
9532 background: linear-gradient(to right, #42A5F5 -40px, #42A5F5 7px, #E3F2FD 7px, #E3F2FD 100%);
9533 }
9534 .edit_mode div.cell.selected {
9535 border-color: #66BB6A;
9536 border-left-width: 0px;
9537 padding-left: 6px;
9538 background: linear-gradient(to right, #66BB6A -40px, #66BB6A 5px, transparent 5px, transparent 100%);
9539 }
9540 @media print {
9541 .edit_mode div.cell.selected {
9542 border-color: transparent;
9543 }
9544 }
9545 .prompt {
9546 /* This needs to be wide enough for 3 digit prompt numbers: In[100]: */
9547 min-width: 14ex;
9548 /* This padding is tuned to match the padding on the CodeMirror editor. */
9549 padding: 0.4em;
9550 margin: 0px;
9551 font-family: monospace;
9552 text-align: right;
9553 /* This has to match that of the the CodeMirror class line-height below */
9554 line-height: 1.21429em;
9555 /* Don't highlight prompt number selection */
9556 -webkit-touch-callout: none;
9557 -webkit-user-select: none;
9558 -khtml-user-select: none;
9559 -moz-user-select: none;
9560 -ms-user-select: none;
9561 user-select: none;
9562 /* Use default cursor */
9563 cursor: default;
9564 }
9565 @media (max-width: 540px) {
9566 .prompt {
9567 text-align: left;
9568 }
9569 }
9570 div.inner_cell {
9571 min-width: 0;
9572 /* Old browsers */
9573 display: -webkit-box;
9574 -webkit-box-orient: vertical;
9575 -webkit-box-align: stretch;
9576 display: -moz-box;
9577 -moz-box-orient: vertical;
9578 -moz-box-align: stretch;
9579 display: box;
9580 box-orient: vertical;
9581 box-align: stretch;
9582 /* Modern browsers */
9583 display: flex;
9584 flex-direction: column;
9585 align-items: stretch;
9586 /* Old browsers */
9587 -webkit-box-flex: 1;
9588 -moz-box-flex: 1;
9589 box-flex: 1;
9590 /* Modern browsers */
9591 flex: 1;
9592 }
9593 /* input_area and input_prompt must match in top border and margin for alignment */
9594 div.input_area {
9595 border: 1px solid #cfcfcf;
9596 border-radius: 2px;
9597 background: #f7f7f7;
9598 line-height: 1.21429em;
9599 }
9600 /* This is needed so that empty prompt areas can collapse to zero height when there
9601 is no content in the output_subarea and the prompt. The main purpose of this is
9602 to make sure that empty JavaScript output_subareas have no height. */
9603 div.prompt:empty {
9604 padding-top: 0;
9605 padding-bottom: 0;
9606 }
9607 div.unrecognized_cell {
9608 padding: 5px 5px 5px 0px;
9609 /* Old browsers */
9610 display: -webkit-box;
9611 -webkit-box-orient: horizontal;
9612 -webkit-box-align: stretch;
9613 display: -moz-box;
9614 -moz-box-orient: horizontal;
9615 -moz-box-align: stretch;
9616 display: box;
9617 box-orient: horizontal;
9618 box-align: stretch;
9619 /* Modern browsers */
9620 display: flex;
9621 flex-direction: row;
9622 align-items: stretch;
9623 }
9624 div.unrecognized_cell .inner_cell {
9625 border-radius: 2px;
9626 padding: 5px;
9627 font-weight: bold;
9628 color: red;
9629 border: 1px solid #cfcfcf;
9630 background: #eaeaea;
9631 }
9632 div.unrecognized_cell .inner_cell a {
9633 color: inherit;
9634 text-decoration: none;
9635 }
9636 div.unrecognized_cell .inner_cell a:hover {
9637 color: inherit;
9638 text-decoration: none;
9639 }
9640 @media (max-width: 540px) {
9641 div.unrecognized_cell > div.prompt {
9642 display: none;
9643 }
9644 }
9645 div.code_cell {
9646 /* avoid page breaking on code cells when printing */
9647 }
9648 @media print {
9649 div.code_cell {
9650 page-break-inside: avoid;
9651 }
9652 }
9653 /* any special styling for code cells that are currently running goes here */
9654 div.input {
9655 page-break-inside: avoid;
9656 /* Old browsers */
9657 display: -webkit-box;
9658 -webkit-box-orient: horizontal;
9659 -webkit-box-align: stretch;
9660 display: -moz-box;
9661 -moz-box-orient: horizontal;
9662 -moz-box-align: stretch;
9663 display: box;
9664 box-orient: horizontal;
9665 box-align: stretch;
9666 /* Modern browsers */
9667 display: flex;
9668 flex-direction: row;
9669 align-items: stretch;
9670 }
9671 @media (max-width: 540px) {
9672 div.input {
9673 /* Old browsers */
9674 display: -webkit-box;
9675 -webkit-box-orient: vertical;
9676 -webkit-box-align: stretch;
9677 display: -moz-box;
9678 -moz-box-orient: vertical;
9679 -moz-box-align: stretch;
9680 display: box;
9681 box-orient: vertical;
9682 box-align: stretch;
9683 /* Modern browsers */
9684 display: flex;
9685 flex-direction: column;
9686 align-items: stretch;
9687 }
9688 }
9689 /* input_area and input_prompt must match in top border and margin for alignment */
9690 div.input_prompt {
9691 color: #303F9F;
9692 border-top: 1px solid transparent;
9693 }
9694 div.input_area > div.highlight {
9695 margin: 0.4em;
9696 border: none;
9697 padding: 0px;
9698 background-color: transparent;
9699 }
9700 div.input_area > div.highlight > pre {
9701 margin: 0px;
9702 border: none;
9703 padding: 0px;
9704 background-color: transparent;
9705 }
9706 /* The following gets added to the <head> if it is detected that the user has a
9707 * monospace font with inconsistent normal/bold/italic height. See
9708 * notebookmain.js. Such fonts will have keywords vertically offset with
9709 * respect to the rest of the text. The user should select a better font.
9710 * See: https://github.com/ipython/ipython/issues/1503
9711 *
9712 * .CodeMirror span {
9713 * vertical-align: bottom;
9714 * }
9715 */
9716 .CodeMirror {
9717 line-height: 1.21429em;
9718 /* Changed from 1em to our global default */
9719 font-size: 14px;
9720 height: auto;
9721 /* Changed to auto to autogrow */
9722 background: none;
9723 /* Changed from white to allow our bg to show through */
9724 }
9725 .CodeMirror-scroll {
9726 /* The CodeMirror docs are a bit fuzzy on if overflow-y should be hidden or visible.*/
9727 /* We have found that if it is visible, vertical scrollbars appear with font size changes.*/
9728 overflow-y: hidden;
9729 overflow-x: auto;
9730 }
9731 .CodeMirror-lines {
9732 /* In CM2, this used to be 0.4em, but in CM3 it went to 4px. We need the em value because */
9733 /* we have set a different line-height and want this to scale with that. */
9734 padding: 0.4em;
9735 }
9736 .CodeMirror-linenumber {
9737 padding: 0 8px 0 4px;
9738 }
9739 .CodeMirror-gutters {
9740 border-bottom-left-radius: 2px;
9741 border-top-left-radius: 2px;
9742 }
9743 .CodeMirror pre {
9744 /* In CM3 this went to 4px from 0 in CM2. We need the 0 value because of how we size */
9745 /* .CodeMirror-lines */
9746 padding: 0;
9747 border: 0;
9748 border-radius: 0;
9749 }
9750 /*
9751
9752 Original style from softwaremaniacs.org (c) Ivan Sagalaev <Maniac@SoftwareManiacs.Org>
9753 Adapted from GitHub theme
9754
9755 */
9756 .highlight-base {
9757 color: #000;
9758 }
9759 .highlight-variable {
9760 color: #000;
9761 }
9762 .highlight-variable-2 {
9763 color: #1a1a1a;
9764 }
9765 .highlight-variable-3 {
9766 color: #333333;
9767 }
9768 .highlight-string {
9769 color: #BA2121;
9770 }
9771 .highlight-comment {
9772 color: #408080;
9773 font-style: italic;
9774 }
9775 .highlight-number {
9776 color: #080;
9777 }
9778 .highlight-atom {
9779 color: #88F;
9780 }
9781 .highlight-keyword {
9782 color: #008000;
9783 font-weight: bold;
9784 }
9785 .highlight-builtin {
9786 color: #008000;
9787 }
9788 .highlight-error {
9789 color: #f00;
9790 }
9791 .highlight-operator {
9792 color: #AA22FF;
9793 font-weight: bold;
9794 }
9795 .highlight-meta {
9796 color: #AA22FF;
9797 }
9798 /* previously not defined, copying from default codemirror */
9799 .highlight-def {
9800 color: #00f;
9801 }
9802 .highlight-string-2 {
9803 color: #f50;
9804 }
9805 .highlight-qualifier {
9806 color: #555;
9807 }
9808 .highlight-bracket {
9809 color: #997;
9810 }
9811 .highlight-tag {
9812 color: #170;
9813 }
9814 .highlight-attribute {
9815 color: #00c;
9816 }
9817 .highlight-header {
9818 color: blue;
9819 }
9820 .highlight-quote {
9821 color: #090;
9822 }
9823 .highlight-link {
9824 color: #00c;
9825 }
9826 /* apply the same style to codemirror */
9827 .cm-s-ipython span.cm-keyword {
9828 color: #008000;
9829 font-weight: bold;
9830 }
9831 .cm-s-ipython span.cm-atom {
9832 color: #88F;
9833 }
9834 .cm-s-ipython span.cm-number {
9835 color: #080;
9836 }
9837 .cm-s-ipython span.cm-def {
9838 color: #00f;
9839 }
9840 .cm-s-ipython span.cm-variable {
9841 color: #000;
9842 }
9843 .cm-s-ipython span.cm-operator {
9844 color: #AA22FF;
9845 font-weight: bold;
9846 }
9847 .cm-s-ipython span.cm-variable-2 {
9848 color: #1a1a1a;
9849 }
9850 .cm-s-ipython span.cm-variable-3 {
9851 color: #333333;
9852 }
9853 .cm-s-ipython span.cm-comment {
9854 color: #408080;
9855 font-style: italic;
9856 }
9857 .cm-s-ipython span.cm-string {
9858 color: #BA2121;
9859 }
9860 .cm-s-ipython span.cm-string-2 {
9861 color: #f50;
9862 }
9863 .cm-s-ipython span.cm-meta {
9864 color: #AA22FF;
9865 }
9866 .cm-s-ipython span.cm-qualifier {
9867 color: #555;
9868 }
9869 .cm-s-ipython span.cm-builtin {
9870 color: #008000;
9871 }
9872 .cm-s-ipython span.cm-bracket {
9873 color: #997;
9874 }
9875 .cm-s-ipython span.cm-tag {
9876 color: #170;
9877 }
9878 .cm-s-ipython span.cm-attribute {
9879 color: #00c;
9880 }
9881 .cm-s-ipython span.cm-header {
9882 color: blue;
9883 }
9884 .cm-s-ipython span.cm-quote {
9885 color: #090;
9886 }
9887 .cm-s-ipython span.cm-link {
9888 color: #00c;
9889 }
9890 .cm-s-ipython span.cm-error {
9891 color: #f00;
9892 }
9893 .cm-s-ipython span.cm-tab {
9894 background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAMCAYAAAAkuj5RAAAAAXNSR0IArs4c6QAAAGFJREFUSMft1LsRQFAQheHPowAKoACx3IgEKtaEHujDjORSgWTH/ZOdnZOcM/sgk/kFFWY0qV8foQwS4MKBCS3qR6ixBJvElOobYAtivseIE120FaowJPN75GMu8j/LfMwNjh4HUpwg4LUAAAAASUVORK5CYII=);
9895 background-position: right;
9896 background-repeat: no-repeat;
9897 }
9898 div.output_wrapper {
9899 /* this position must be relative to enable descendents to be absolute within it */
9900 position: relative;
9901 /* Old browsers */
9902 display: -webkit-box;
9903 -webkit-box-orient: vertical;
9904 -webkit-box-align: stretch;
9905 display: -moz-box;
9906 -moz-box-orient: vertical;
9907 -moz-box-align: stretch;
9908 display: box;
9909 box-orient: vertical;
9910 box-align: stretch;
9911 /* Modern browsers */
9912 display: flex;
9913 flex-direction: column;
9914 align-items: stretch;
9915 z-index: 1;
9916 }
9917 /* class for the output area when it should be height-limited */
9918 div.output_scroll {
9919 /* ideally, this would be max-height, but FF barfs all over that */
9920 height: 24em;
9921 /* FF needs this *and the wrapper* to specify full width, or it will shrinkwrap */
9922 width: 100%;
9923 overflow: auto;
9924 border-radius: 2px;
9925 -webkit-box-shadow: inset 0 2px 8px rgba(0, 0, 0, 0.8);
9926 box-shadow: inset 0 2px 8px rgba(0, 0, 0, 0.8);
9927 display: block;
9928 }
9929 /* output div while it is collapsed */
9930 div.output_collapsed {
9931 margin: 0px;
9932 padding: 0px;
9933 /* Old browsers */
9934 display: -webkit-box;
9935 -webkit-box-orient: vertical;
9936 -webkit-box-align: stretch;
9937 display: -moz-box;
9938 -moz-box-orient: vertical;
9939 -moz-box-align: stretch;
9940 display: box;
9941 box-orient: vertical;
9942 box-align: stretch;
9943 /* Modern browsers */
9944 display: flex;
9945 flex-direction: column;
9946 align-items: stretch;
9947 }
9948 div.out_prompt_overlay {
9949 height: 100%;
9950 padding: 0px 0.4em;
9951 position: absolute;
9952 border-radius: 2px;
9953 }
9954 div.out_prompt_overlay:hover {
9955 /* use inner shadow to get border that is computed the same on WebKit/FF */
9956 -webkit-box-shadow: inset 0 0 1px #000;
9957 box-shadow: inset 0 0 1px #000;
9958 background: rgba(240, 240, 240, 0.5);
9959 }
9960 div.output_prompt {
9961 color: #D84315;
9962 }
9963 /* This class is the outer container of all output sections. */
9964 div.output_area {
9965 padding: 0px;
9966 page-break-inside: avoid;
9967 /* Old browsers */
9968 display: -webkit-box;
9969 -webkit-box-orient: horizontal;
9970 -webkit-box-align: stretch;
9971 display: -moz-box;
9972 -moz-box-orient: horizontal;
9973 -moz-box-align: stretch;
9974 display: box;
9975 box-orient: horizontal;
9976 box-align: stretch;
9977 /* Modern browsers */
9978 display: flex;
9979 flex-direction: row;
9980 align-items: stretch;
9981 }
9982 div.output_area .MathJax_Display {
9983 text-align: left !important;
9984 }
9985 div.output_area .rendered_html table {
9986 margin-left: 0;
9987 margin-right: 0;
9988 }
9989 div.output_area .rendered_html img {
9990 margin-left: 0;
9991 margin-right: 0;
9992 }
9993 div.output_area img,
9994 div.output_area svg {
9995 max-width: 100%;
9996 height: auto;
9997 }
9998 div.output_area img.unconfined,
9999 div.output_area svg.unconfined {
10000 max-width: none;
10001 }
10002 /* This is needed to protect the pre formating from global settings such
10003 as that of bootstrap */
10004 .output {
10005 /* Old browsers */
10006 display: -webkit-box;
10007 -webkit-box-orient: vertical;
10008 -webkit-box-align: stretch;
10009 display: -moz-box;
10010 -moz-box-orient: vertical;
10011 -moz-box-align: stretch;
10012 display: box;
10013 box-orient: vertical;
10014 box-align: stretch;
10015 /* Modern browsers */
10016 display: flex;
10017 flex-direction: column;
10018 align-items: stretch;
10019 }
10020 @media (max-width: 540px) {
10021 div.output_area {
10022 /* Old browsers */
10023 display: -webkit-box;
10024 -webkit-box-orient: vertical;
10025 -webkit-box-align: stretch;
10026 display: -moz-box;
10027 -moz-box-orient: vertical;
10028 -moz-box-align: stretch;
10029 display: box;
10030 box-orient: vertical;
10031 box-align: stretch;
10032 /* Modern browsers */
10033 display: flex;
10034 flex-direction: column;
10035 align-items: stretch;
10036 }
10037 }
10038 div.output_area pre {
10039 margin: 0;
10040 padding: 0;
10041 border: 0;
10042 vertical-align: baseline;
10043 color: black;
10044 background-color: transparent;
10045 border-radius: 0;
10046 }
10047 /* This class is for the output subarea inside the output_area and after
10048 the prompt div. */
10049 div.output_subarea {
10050 overflow-x: auto;
10051 padding: 0.4em;
10052 /* Old browsers */
10053 -webkit-box-flex: 1;
10054 -moz-box-flex: 1;
10055 box-flex: 1;
10056 /* Modern browsers */
10057 flex: 1;
10058 max-width: calc(100% - 14ex);
10059 }
10060 div.output_scroll div.output_subarea {
10061 overflow-x: visible;
10062 }
10063 /* The rest of the output_* classes are for special styling of the different
10064 output types */
10065 /* all text output has this class: */
10066 div.output_text {
10067 text-align: left;
10068 color: #000;
10069 /* This has to match that of the the CodeMirror class line-height below */
10070 line-height: 1.21429em;
10071 }
10072 /* stdout/stderr are 'text' as well as 'stream', but execute_result/error are *not* streams */
10073 div.output_stderr {
10074 background: #fdd;
10075 /* very light red background for stderr */
10076 }
10077 div.output_latex {
10078 text-align: left;
10079 }
10080 /* Empty output_javascript divs should have no height */
10081 div.output_javascript:empty {
10082 padding: 0;
10083 }
10084 .js-error {
10085 color: darkred;
10086 }
10087 /* raw_input styles */
10088 div.raw_input_container {
10089 line-height: 1.21429em;
10090 padding-top: 5px;
10091 }
10092 pre.raw_input_prompt {
10093 /* nothing needed here. */
10094 }
10095 input.raw_input {
10096 font-family: monospace;
10097 font-size: inherit;
10098 color: inherit;
10099 width: auto;
10100 /* make sure input baseline aligns with prompt */
10101 vertical-align: baseline;
10102 /* padding + margin = 0.5em between prompt and cursor */
10103 padding: 0em 0.25em;
10104 margin: 0em 0.25em;
10105 }
10106 input.raw_input:focus {
10107 box-shadow: none;
10108 }
10109 p.p-space {
10110 margin-bottom: 10px;
10111 }
10112 div.output_unrecognized {
10113 padding: 5px;
10114 font-weight: bold;
10115 color: red;
10116 }
10117 div.output_unrecognized a {
10118 color: inherit;
10119 text-decoration: none;
10120 }
10121 div.output_unrecognized a:hover {
10122 color: inherit;
10123 text-decoration: none;
10124 }
10125 .rendered_html {
10126 color: #000;
10127 /* any extras will just be numbers: */
10128 }
10129 .rendered_html em {
10130 font-style: italic;
10131 }
10132 .rendered_html strong {
10133 font-weight: bold;
10134 }
10135 .rendered_html u {
10136 text-decoration: underline;
10137 }
10138 .rendered_html :link {
10139 text-decoration: underline;
10140 }
10141 .rendered_html :visited {
10142 text-decoration: underline;
10143 }
10144 .rendered_html h1 {
10145 font-size: 185.7%;
10146 margin: 1.08em 0 0 0;
10147 font-weight: bold;
10148 line-height: 1.0;
10149 }
10150 .rendered_html h2 {
10151 font-size: 157.1%;
10152 margin: 1.27em 0 0 0;
10153 font-weight: bold;
10154 line-height: 1.0;
10155 }
10156 .rendered_html h3 {
10157 font-size: 128.6%;
10158 margin: 1.55em 0 0 0;
10159 font-weight: bold;
10160 line-height: 1.0;
10161 }
10162 .rendered_html h4 {
10163 font-size: 100%;
10164 margin: 2em 0 0 0;
10165 font-weight: bold;
10166 line-height: 1.0;
10167 }
10168 .rendered_html h5 {
10169 font-size: 100%;
10170 margin: 2em 0 0 0;
10171 font-weight: bold;
10172 line-height: 1.0;
10173 font-style: italic;
10174 }
10175 .rendered_html h6 {
10176 font-size: 100%;
10177 margin: 2em 0 0 0;
10178 font-weight: bold;
10179 line-height: 1.0;
10180 font-style: italic;
10181 }
10182 .rendered_html h1:first-child {
10183 margin-top: 0.538em;
10184 }
10185 .rendered_html h2:first-child {
10186 margin-top: 0.636em;
10187 }
10188 .rendered_html h3:first-child {
10189 margin-top: 0.777em;
10190 }
10191 .rendered_html h4:first-child {
10192 margin-top: 1em;
10193 }
10194 .rendered_html h5:first-child {
10195 margin-top: 1em;
10196 }
10197 .rendered_html h6:first-child {
10198 margin-top: 1em;
10199 }
10200 .rendered_html ul {
10201 list-style: disc;
10202 margin: 0em 2em;
10203 padding-left: 0px;
10204 }
10205 .rendered_html ul ul {
10206 list-style: square;
10207 margin: 0em 2em;
10208 }
10209 .rendered_html ul ul ul {
10210 list-style: circle;
10211 margin: 0em 2em;
10212 }
10213 .rendered_html ol {
10214 list-style: decimal;
10215 margin: 0em 2em;
10216 padding-left: 0px;
10217 }
10218 .rendered_html ol ol {
10219 list-style: upper-alpha;
10220 margin: 0em 2em;
10221 }
10222 .rendered_html ol ol ol {
10223 list-style: lower-alpha;
10224 margin: 0em 2em;
10225 }
10226 .rendered_html ol ol ol ol {
10227 list-style: lower-roman;
10228 margin: 0em 2em;
10229 }
10230 .rendered_html ol ol ol ol ol {
10231 list-style: decimal;
10232 margin: 0em 2em;
10233 }
10234 .rendered_html * + ul {
10235 margin-top: 1em;
10236 }
10237 .rendered_html * + ol {
10238 margin-top: 1em;
10239 }
10240 .rendered_html hr {
10241 color: black;
10242 background-color: black;
10243 }
10244 .rendered_html pre {
10245 margin: 1em 2em;
10246 }
10247 .rendered_html pre,
10248 .rendered_html code {
10249 border: 0;
10250 background-color: #fff;
10251 color: #000;
10252 font-size: 100%;
10253 padding: 0px;
10254 }
10255 .rendered_html blockquote {
10256 margin: 1em 2em;
10257 }
10258 .rendered_html table {
10259 margin-left: auto;
10260 margin-right: auto;
10261 border: 1px solid black;
10262 border-collapse: collapse;
10263 }
10264 .rendered_html tr,
10265 .rendered_html th,
10266 .rendered_html td {
10267 border: 1px solid black;
10268 border-collapse: collapse;
10269 margin: 1em 2em;
10270 }
10271 .rendered_html td,
10272 .rendered_html th {
10273 text-align: left;
10274 vertical-align: middle;
10275 padding: 4px;
10276 }
10277 .rendered_html th {
10278 font-weight: bold;
10279 }
10280 .rendered_html * + table {
10281 margin-top: 1em;
10282 }
10283 .rendered_html p {
10284 text-align: left;
10285 }
10286 .rendered_html * + p {
10287 margin-top: 1em;
10288 }
10289 .rendered_html img {
10290 display: block;
10291 margin-left: auto;
10292 margin-right: auto;
10293 }
10294 .rendered_html * + img {
10295 margin-top: 1em;
10296 }
10297 .rendered_html img,
10298 .rendered_html svg {
10299 max-width: 100%;
10300 height: auto;
10301 }
10302 .rendered_html img.unconfined,
10303 .rendered_html svg.unconfined {
10304 max-width: none;
10305 }
10306 div.text_cell {
10307 /* Old browsers */
10308 display: -webkit-box;
10309 -webkit-box-orient: horizontal;
10310 -webkit-box-align: stretch;
10311 display: -moz-box;
10312 -moz-box-orient: horizontal;
10313 -moz-box-align: stretch;
10314 display: box;
10315 box-orient: horizontal;
10316 box-align: stretch;
10317 /* Modern browsers */
10318 display: flex;
10319 flex-direction: row;
10320 align-items: stretch;
10321 }
10322 @media (max-width: 540px) {
10323 div.text_cell > div.prompt {
10324 display: none;
10325 }
10326 }
10327 div.text_cell_render {
10328 /*font-family: "Helvetica Neue", Arial, Helvetica, Geneva, sans-serif;*/
10329 outline: none;
10330 resize: none;
10331 width: inherit;
10332 border-style: none;
10333 padding: 0.5em 0.5em 0.5em 0.4em;
10334 color: #000;
10335 box-sizing: border-box;
10336 -moz-box-sizing: border-box;
10337 -webkit-box-sizing: border-box;
10338 }
10339 a.anchor-link:link {
10340 text-decoration: none;
10341 padding: 0px 20px;
10342 visibility: hidden;
10343 }
10344 h1:hover .anchor-link,
10345 h2:hover .anchor-link,
10346 h3:hover .anchor-link,
10347 h4:hover .anchor-link,
10348 h5:hover .anchor-link,
10349 h6:hover .anchor-link {
10350 visibility: visible;
10351 }
10352 .text_cell.rendered .input_area {
10353 display: none;
10354 }
10355 .text_cell.rendered .rendered_html {
10356 overflow-x: auto;
10357 overflow-y: hidden;
10358 }
10359 .text_cell.unrendered .text_cell_render {
10360 display: none;
10361 }
10362 .cm-header-1,
10363 .cm-header-2,
10364 .cm-header-3,
10365 .cm-header-4,
10366 .cm-header-5,
10367 .cm-header-6 {
10368 font-weight: bold;
10369 font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
10370 }
10371 .cm-header-1 {
10372 font-size: 185.7%;
10373 }
10374 .cm-header-2 {
10375 font-size: 157.1%;
10376 }
10377 .cm-header-3 {
10378 font-size: 128.6%;
10379 }
10380 .cm-header-4 {
10381 font-size: 110%;
10382 }
10383 .cm-header-5 {
10384 font-size: 100%;
10385 font-style: italic;
10386 }
10387 .cm-header-6 {
10388 font-size: 100%;
10389 font-style: italic;
10390 }
10391 /*!
10392 *
10393 * IPython notebook webapp
10394 *
10395 */
10396 @media (max-width: 767px) {
10397 .notebook_app {
10398 padding-left: 0px;
10399 padding-right: 0px;
10400 }
10401 }
10402 #ipython-main-app {
10403 box-sizing: border-box;
10404 -moz-box-sizing: border-box;
10405 -webkit-box-sizing: border-box;
10406 height: 100%;
10407 }
10408 div#notebook_panel {
10409 margin: 0px;
10410 padding: 0px;
10411 box-sizing: border-box;
10412 -moz-box-sizing: border-box;
10413 -webkit-box-sizing: border-box;
10414 height: 100%;
10415 }
10416 div#notebook {
10417 font-size: 14px;
10418 line-height: 20px;
10419 overflow-y: hidden;
10420 overflow-x: auto;
10421 width: 100%;
10422 /* This spaces the page away from the edge of the notebook area */
10423 padding-top: 20px;
10424 margin: 0px;
10425 outline: none;
10426 box-sizing: border-box;
10427 -moz-box-sizing: border-box;
10428 -webkit-box-sizing: border-box;
10429 min-height: 100%;
10430 }
10431 @media not print {
10432 #notebook-container {
10433 padding: 15px;
10434 background-color: #fff;
10435 min-height: 0;
10436 -webkit-box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
10437 box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
10438 }
10439 }
10440 @media print {
10441 #notebook-container {
10442 width: 100%;
10443 }
10444 }
10445 div.ui-widget-content {
10446 border: 1px solid #ababab;
10447 outline: none;
10448 }
10449 pre.dialog {
10450 background-color: #f7f7f7;
10451 border: 1px solid #ddd;
10452 border-radius: 2px;
10453 padding: 0.4em;
10454 padding-left: 2em;
10455 }
10456 p.dialog {
10457 padding: 0.2em;
10458 }
10459 /* Word-wrap output correctly. This is the CSS3 spelling, though Firefox seems
10460 to not honor it correctly. Webkit browsers (Chrome, rekonq, Safari) do.
10461 */
10462 pre,
10463 code,
10464 kbd,
10465 samp {
10466 white-space: pre-wrap;
10467 }
10468 #fonttest {
10469 font-family: monospace;
10470 }
10471 p {
10472 margin-bottom: 0;
10473 }
10474 .end_space {
10475 min-height: 100px;
10476 transition: height .2s ease;
10477 }
10478 .notebook_app > #header {
10479 -webkit-box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
10480 box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
10481 }
10482 @media not print {
10483 .notebook_app {
10484 background-color: #EEE;
10485 }
10486 }
10487 kbd {
10488 border-style: solid;
10489 border-width: 1px;
10490 box-shadow: none;
10491 margin: 2px;
10492 padding-left: 2px;
10493 padding-right: 2px;
10494 padding-top: 1px;
10495 padding-bottom: 1px;
10496 }
10497 /* CSS for the cell toolbar */
10498 .celltoolbar {
10499 border: thin solid #CFCFCF;
10500 border-bottom: none;
10501 background: #EEE;
10502 border-radius: 2px 2px 0px 0px;
10503 width: 100%;
10504 height: 29px;
10505 padding-right: 4px;
10506 /* Old browsers */
10507 display: -webkit-box;
10508 -webkit-box-orient: horizontal;
10509 -webkit-box-align: stretch;
10510 display: -moz-box;
10511 -moz-box-orient: horizontal;
10512 -moz-box-align: stretch;
10513 display: box;
10514 box-orient: horizontal;
10515 box-align: stretch;
10516 /* Modern browsers */
10517 display: flex;
10518 flex-direction: row;
10519 align-items: stretch;
10520 /* Old browsers */
10521 -webkit-box-pack: end;
10522 -moz-box-pack: end;
10523 box-pack: end;
10524 /* Modern browsers */
10525 justify-content: flex-end;
10526 display: -webkit-flex;
10527 }
10528 @media print {
10529 .celltoolbar {
10530 display: none;
10531 }
10532 }
10533 .ctb_hideshow {
10534 display: none;
10535 vertical-align: bottom;
10536 }
10537 /* ctb_show is added to the ctb_hideshow div to show the cell toolbar.
10538 Cell toolbars are only shown when the ctb_global_show class is also set.
10539 */
10540 .ctb_global_show .ctb_show.ctb_hideshow {
10541 display: block;
10542 }
10543 .ctb_global_show .ctb_show + .input_area,
10544 .ctb_global_show .ctb_show + div.text_cell_input,
10545 .ctb_global_show .ctb_show ~ div.text_cell_render {
10546 border-top-right-radius: 0px;
10547 border-top-left-radius: 0px;
10548 }
10549 .ctb_global_show .ctb_show ~ div.text_cell_render {
10550 border: 1px solid #cfcfcf;
10551 }
10552 .celltoolbar {
10553 font-size: 87%;
10554 padding-top: 3px;
10555 }
10556 .celltoolbar select {
10557 display: block;
10558 width: 100%;
10559 height: 32px;
10560 padding: 6px 12px;
10561 font-size: 13px;
10562 line-height: 1.42857143;
10563 color: #555555;
10564 background-color: #fff;
10565 background-image: none;
10566 border: 1px solid #ccc;
10567 border-radius: 2px;
10568 -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
10569 box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075);
10570 -webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
10571 -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
10572 transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
10573 height: 30px;
10574 padding: 5px 10px;
10575 font-size: 12px;
10576 line-height: 1.5;
10577 border-radius: 1px;
10578 width: inherit;
10579 font-size: inherit;
10580 height: 22px;
10581 padding: 0px;
10582 display: inline-block;
10583 }
10584 .celltoolbar select:focus {
10585 border-color: #66afe9;
10586 outline: 0;
10587 -webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
10588 box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
10589 }
10590 .celltoolbar select::-moz-placeholder {
10591 color: #999;
10592 opacity: 1;
10593 }
10594 .celltoolbar select:-ms-input-placeholder {
10595 color: #999;
10596 }
10597 .celltoolbar select::-webkit-input-placeholder {
10598 color: #999;
10599 }
10600 .celltoolbar select::-ms-expand {
10601 border: 0;
10602 background-color: transparent;
10603 }
10604 .celltoolbar select[disabled],
10605 .celltoolbar select[readonly],
10606 fieldset[disabled] .celltoolbar select {
10607 background-color: #eeeeee;
10608 opacity: 1;
10609 }
10610 .celltoolbar select[disabled],
10611 fieldset[disabled] .celltoolbar select {
10612 cursor: not-allowed;
10613 }
10614 textarea.celltoolbar select {
10615 height: auto;
10616 }
10617 select.celltoolbar select {
10618 height: 30px;
10619 line-height: 30px;
10620 }
10621 textarea.celltoolbar select,
10622 select[multiple].celltoolbar select {
10623 height: auto;
10624 }
10625 .celltoolbar label {
10626 margin-left: 5px;
10627 margin-right: 5px;
10628 }
10629 .completions {
10630 position: absolute;
10631 z-index: 110;
10632 overflow: hidden;
10633 border: 1px solid #ababab;
10634 border-radius: 2px;
10635 -webkit-box-shadow: 0px 6px 10px -1px #adadad;
10636 box-shadow: 0px 6px 10px -1px #adadad;
10637 line-height: 1;
10638 }
10639 .completions select {
10640 background: white;
10641 outline: none;
10642 border: none;
10643 padding: 0px;
10644 margin: 0px;
10645 overflow: auto;
10646 font-family: monospace;
10647 font-size: 110%;
10648 color: #000;
10649 width: auto;
10650 }
10651 .completions select option.context {
10652 color: #286090;
10653 }
10654 #kernel_logo_widget {
10655 float: right !important;
10656 float: right;
10657 }
10658 #kernel_logo_widget .current_kernel_logo {
10659 display: none;
10660 margin-top: -1px;
10661 margin-bottom: -1px;
10662 width: 32px;
10663 height: 32px;
10664 }
10665 #menubar {
10666 box-sizing: border-box;
10667 -moz-box-sizing: border-box;
10668 -webkit-box-sizing: border-box;
10669 margin-top: 1px;
10670 }
10671 #menubar .navbar {
10672 border-top: 1px;
10673 border-radius: 0px 0px 2px 2px;
10674 margin-bottom: 0px;
10675 }
10676 #menubar .navbar-toggle {
10677 float: left;
10678 padding-top: 7px;
10679 padding-bottom: 7px;
10680 border: none;
10681 }
10682 #menubar .navbar-collapse {
10683 clear: left;
10684 }
10685 .nav-wrapper {
10686 border-bottom: 1px solid #e7e7e7;
10687 }
10688 i.menu-icon {
10689 padding-top: 4px;
10690 }
10691 ul#help_menu li a {
10692 overflow: hidden;
10693 padding-right: 2.2em;
10694 }
10695 ul#help_menu li a i {
10696 margin-right: -1.2em;
10697 }
10698 .dropdown-submenu {
10699 position: relative;
10700 }
10701 .dropdown-submenu > .dropdown-menu {
10702 top: 0;
10703 left: 100%;
10704 margin-top: -6px;
10705 margin-left: -1px;
10706 }
10707 .dropdown-submenu:hover > .dropdown-menu {
10708 display: block;
10709 }
10710 .dropdown-submenu > a:after {
10711 display: inline-block;
10712 font: normal normal normal 14px/1 FontAwesome;
10713 font-size: inherit;
10714 text-rendering: auto;
10715 -webkit-font-smoothing: antialiased;
10716 -moz-osx-font-smoothing: grayscale;
10717 display: block;
10718 content: "\f0da";
10719 float: right;
10720 color: #333333;
10721 margin-top: 2px;
10722 margin-right: -10px;
10723 }
10724 .dropdown-submenu > a:after.pull-left {
10725 margin-right: .3em;
10726 }
10727 .dropdown-submenu > a:after.pull-right {
10728 margin-left: .3em;
10729 }
10730 .dropdown-submenu:hover > a:after {
10731 color: #262626;
10732 }
10733 .dropdown-submenu.pull-left {
10734 float: none;
10735 }
10736 .dropdown-submenu.pull-left > .dropdown-menu {
10737 left: -100%;
10738 margin-left: 10px;
10739 }
10740 #notification_area {
10741 float: right !important;
10742 float: right;
10743 z-index: 10;
10744 }
10745 .indicator_area {
10746 float: right !important;
10747 float: right;
10748 color: #777;
10749 margin-left: 5px;
10750 margin-right: 5px;
10751 width: 11px;
10752 z-index: 10;
10753 text-align: center;
10754 width: auto;
10755 }
10756 #kernel_indicator {
10757 float: right !important;
10758 float: right;
10759 color: #777;
10760 margin-left: 5px;
10761 margin-right: 5px;
10762 width: 11px;
10763 z-index: 10;
10764 text-align: center;
10765 width: auto;
10766 border-left: 1px solid;
10767 }
10768 #kernel_indicator .kernel_indicator_name {
10769 padding-left: 5px;
10770 padding-right: 5px;
10771 }
10772 #modal_indicator {
10773 float: right !important;
10774 float: right;
10775 color: #777;
10776 margin-left: 5px;
10777 margin-right: 5px;
10778 width: 11px;
10779 z-index: 10;
10780 text-align: center;
10781 width: auto;
10782 }
10783 #readonly-indicator {
10784 float: right !important;
10785 float: right;
10786 color: #777;
10787 margin-left: 5px;
10788 margin-right: 5px;
10789 width: 11px;
10790 z-index: 10;
10791 text-align: center;
10792 width: auto;
10793 margin-top: 2px;
10794 margin-bottom: 0px;
10795 margin-left: 0px;
10796 margin-right: 0px;
10797 display: none;
10798 }
10799 .modal_indicator:before {
10800 width: 1.28571429em;
10801 text-align: center;
10802 }
10803 .edit_mode .modal_indicator:before {
10804 display: inline-block;
10805 font: normal normal normal 14px/1 FontAwesome;
10806 font-size: inherit;
10807 text-rendering: auto;
10808 -webkit-font-smoothing: antialiased;
10809 -moz-osx-font-smoothing: grayscale;
10810 content: "\f040";
10811 }
10812 .edit_mode .modal_indicator:before.pull-left {
10813 margin-right: .3em;
10814 }
10815 .edit_mode .modal_indicator:before.pull-right {
10816 margin-left: .3em;
10817 }
10818 .command_mode .modal_indicator:before {
10819 display: inline-block;
10820 font: normal normal normal 14px/1 FontAwesome;
10821 font-size: inherit;
10822 text-rendering: auto;
10823 -webkit-font-smoothing: antialiased;
10824 -moz-osx-font-smoothing: grayscale;
10825 content: ' ';
10826 }
10827 .command_mode .modal_indicator:before.pull-left {
10828 margin-right: .3em;
10829 }
10830 .command_mode .modal_indicator:before.pull-right {
10831 margin-left: .3em;
10832 }
10833 .kernel_idle_icon:before {
10834 display: inline-block;
10835 font: normal normal normal 14px/1 FontAwesome;
10836 font-size: inherit;
10837 text-rendering: auto;
10838 -webkit-font-smoothing: antialiased;
10839 -moz-osx-font-smoothing: grayscale;
10840 content: "\f10c";
10841 }
10842 .kernel_idle_icon:before.pull-left {
10843 margin-right: .3em;
10844 }
10845 .kernel_idle_icon:before.pull-right {
10846 margin-left: .3em;
10847 }
10848 .kernel_busy_icon:before {
10849 display: inline-block;
10850 font: normal normal normal 14px/1 FontAwesome;
10851 font-size: inherit;
10852 text-rendering: auto;
10853 -webkit-font-smoothing: antialiased;
10854 -moz-osx-font-smoothing: grayscale;
10855 content: "\f111";
10856 }
10857 .kernel_busy_icon:before.pull-left {
10858 margin-right: .3em;
10859 }
10860 .kernel_busy_icon:before.pull-right {
10861 margin-left: .3em;
10862 }
10863 .kernel_dead_icon:before {
10864 display: inline-block;
10865 font: normal normal normal 14px/1 FontAwesome;
10866 font-size: inherit;
10867 text-rendering: auto;
10868 -webkit-font-smoothing: antialiased;
10869 -moz-osx-font-smoothing: grayscale;
10870 content: "\f1e2";
10871 }
10872 .kernel_dead_icon:before.pull-left {
10873 margin-right: .3em;
10874 }
10875 .kernel_dead_icon:before.pull-right {
10876 margin-left: .3em;
10877 }
10878 .kernel_disconnected_icon:before {
10879 display: inline-block;
10880 font: normal normal normal 14px/1 FontAwesome;
10881 font-size: inherit;
10882 text-rendering: auto;
10883 -webkit-font-smoothing: antialiased;
10884 -moz-osx-font-smoothing: grayscale;
10885 content: "\f127";
10886 }
10887 .kernel_disconnected_icon:before.pull-left {
10888 margin-right: .3em;
10889 }
10890 .kernel_disconnected_icon:before.pull-right {
10891 margin-left: .3em;
10892 }
10893 .notification_widget {
10894 color: #777;
10895 z-index: 10;
10896 background: rgba(240, 240, 240, 0.5);
10897 margin-right: 4px;
10898 color: #333;
10899 background-color: #fff;
10900 border-color: #ccc;
10901 }
10902 .notification_widget:focus,
10903 .notification_widget.focus {
10904 color: #333;
10905 background-color: #e6e6e6;
10906 border-color: #8c8c8c;
10907 }
10908 .notification_widget:hover {
10909 color: #333;
10910 background-color: #e6e6e6;
10911 border-color: #adadad;
10912 }
10913 .notification_widget:active,
10914 .notification_widget.active,
10915 .open > .dropdown-toggle.notification_widget {
10916 color: #333;
10917 background-color: #e6e6e6;
10918 border-color: #adadad;
10919 }
10920 .notification_widget:active:hover,
10921 .notification_widget.active:hover,
10922 .open > .dropdown-toggle.notification_widget:hover,
10923 .notification_widget:active:focus,
10924 .notification_widget.active:focus,
10925 .open > .dropdown-toggle.notification_widget:focus,
10926 .notification_widget:active.focus,
10927 .notification_widget.active.focus,
10928 .open > .dropdown-toggle.notification_widget.focus {
10929 color: #333;
10930 background-color: #d4d4d4;
10931 border-color: #8c8c8c;
10932 }
10933 .notification_widget:active,
10934 .notification_widget.active,
10935 .open > .dropdown-toggle.notification_widget {
10936 background-image: none;
10937 }
10938 .notification_widget.disabled:hover,
10939 .notification_widget[disabled]:hover,
10940 fieldset[disabled] .notification_widget:hover,
10941 .notification_widget.disabled:focus,
10942 .notification_widget[disabled]:focus,
10943 fieldset[disabled] .notification_widget:focus,
10944 .notification_widget.disabled.focus,
10945 .notification_widget[disabled].focus,
10946 fieldset[disabled] .notification_widget.focus {
10947 background-color: #fff;
10948 border-color: #ccc;
10949 }
10950 .notification_widget .badge {
10951 color: #fff;
10952 background-color: #333;
10953 }
10954 .notification_widget.warning {
10955 color: #fff;
10956 background-color: #f0ad4e;
10957 border-color: #eea236;
10958 }
10959 .notification_widget.warning:focus,
10960 .notification_widget.warning.focus {
10961 color: #fff;
10962 background-color: #ec971f;
10963 border-color: #985f0d;
10964 }
10965 .notification_widget.warning:hover {
10966 color: #fff;
10967 background-color: #ec971f;
10968 border-color: #d58512;
10969 }
10970 .notification_widget.warning:active,
10971 .notification_widget.warning.active,
10972 .open > .dropdown-toggle.notification_widget.warning {
10973 color: #fff;
10974 background-color: #ec971f;
10975 border-color: #d58512;
10976 }
10977 .notification_widget.warning:active:hover,
10978 .notification_widget.warning.active:hover,
10979 .open > .dropdown-toggle.notification_widget.warning:hover,
10980 .notification_widget.warning:active:focus,
10981 .notification_widget.warning.active:focus,
10982 .open > .dropdown-toggle.notification_widget.warning:focus,
10983 .notification_widget.warning:active.focus,
10984 .notification_widget.warning.active.focus,
10985 .open > .dropdown-toggle.notification_widget.warning.focus {
10986 color: #fff;
10987 background-color: #d58512;
10988 border-color: #985f0d;
10989 }
10990 .notification_widget.warning:active,
10991 .notification_widget.warning.active,
10992 .open > .dropdown-toggle.notification_widget.warning {
10993 background-image: none;
10994 }
10995 .notification_widget.warning.disabled:hover,
10996 .notification_widget.warning[disabled]:hover,
10997 fieldset[disabled] .notification_widget.warning:hover,
10998 .notification_widget.warning.disabled:focus,
10999 .notification_widget.warning[disabled]:focus,
11000 fieldset[disabled] .notification_widget.warning:focus,
11001 .notification_widget.warning.disabled.focus,
11002 .notification_widget.warning[disabled].focus,
11003 fieldset[disabled] .notification_widget.warning.focus {
11004 background-color: #f0ad4e;
11005 border-color: #eea236;
11006 }
11007 .notification_widget.warning .badge {
11008 color: #f0ad4e;
11009 background-color: #fff;
11010 }
11011 .notification_widget.success {
11012 color: #fff;
11013 background-color: #5cb85c;
11014 border-color: #4cae4c;
11015 }
11016 .notification_widget.success:focus,
11017 .notification_widget.success.focus {
11018 color: #fff;
11019 background-color: #449d44;
11020 border-color: #255625;
11021 }
11022 .notification_widget.success:hover {
11023 color: #fff;
11024 background-color: #449d44;
11025 border-color: #398439;
11026 }
11027 .notification_widget.success:active,
11028 .notification_widget.success.active,
11029 .open > .dropdown-toggle.notification_widget.success {
11030 color: #fff;
11031 background-color: #449d44;
11032 border-color: #398439;
11033 }
11034 .notification_widget.success:active:hover,
11035 .notification_widget.success.active:hover,
11036 .open > .dropdown-toggle.notification_widget.success:hover,
11037 .notification_widget.success:active:focus,
11038 .notification_widget.success.active:focus,
11039 .open > .dropdown-toggle.notification_widget.success:focus,
11040 .notification_widget.success:active.focus,
11041 .notification_widget.success.active.focus,
11042 .open > .dropdown-toggle.notification_widget.success.focus {
11043 color: #fff;
11044 background-color: #398439;
11045 border-color: #255625;
11046 }
11047 .notification_widget.success:active,
11048 .notification_widget.success.active,
11049 .open > .dropdown-toggle.notification_widget.success {
11050 background-image: none;
11051 }
11052 .notification_widget.success.disabled:hover,
11053 .notification_widget.success[disabled]:hover,
11054 fieldset[disabled] .notification_widget.success:hover,
11055 .notification_widget.success.disabled:focus,
11056 .notification_widget.success[disabled]:focus,
11057 fieldset[disabled] .notification_widget.success:focus,
11058 .notification_widget.success.disabled.focus,
11059 .notification_widget.success[disabled].focus,
11060 fieldset[disabled] .notification_widget.success.focus {
11061 background-color: #5cb85c;
11062 border-color: #4cae4c;
11063 }
11064 .notification_widget.success .badge {
11065 color: #5cb85c;
11066 background-color: #fff;
11067 }
11068 .notification_widget.info {
11069 color: #fff;
11070 background-color: #5bc0de;
11071 border-color: #46b8da;
11072 }
11073 .notification_widget.info:focus,
11074 .notification_widget.info.focus {
11075 color: #fff;
11076 background-color: #31b0d5;
11077 border-color: #1b6d85;
11078 }
11079 .notification_widget.info:hover {
11080 color: #fff;
11081 background-color: #31b0d5;
11082 border-color: #269abc;
11083 }
11084 .notification_widget.info:active,
11085 .notification_widget.info.active,
11086 .open > .dropdown-toggle.notification_widget.info {
11087 color: #fff;
11088 background-color: #31b0d5;
11089 border-color: #269abc;
11090 }
11091 .notification_widget.info:active:hover,
11092 .notification_widget.info.active:hover,
11093 .open > .dropdown-toggle.notification_widget.info:hover,
11094 .notification_widget.info:active:focus,
11095 .notification_widget.info.active:focus,
11096 .open > .dropdown-toggle.notification_widget.info:focus,
11097 .notification_widget.info:active.focus,
11098 .notification_widget.info.active.focus,
11099 .open > .dropdown-toggle.notification_widget.info.focus {
11100 color: #fff;
11101 background-color: #269abc;
11102 border-color: #1b6d85;
11103 }
11104 .notification_widget.info:active,
11105 .notification_widget.info.active,
11106 .open > .dropdown-toggle.notification_widget.info {
11107 background-image: none;
11108 }
11109 .notification_widget.info.disabled:hover,
11110 .notification_widget.info[disabled]:hover,
11111 fieldset[disabled] .notification_widget.info:hover,
11112 .notification_widget.info.disabled:focus,
11113 .notification_widget.info[disabled]:focus,
11114 fieldset[disabled] .notification_widget.info:focus,
11115 .notification_widget.info.disabled.focus,
11116 .notification_widget.info[disabled].focus,
11117 fieldset[disabled] .notification_widget.info.focus {
11118 background-color: #5bc0de;
11119 border-color: #46b8da;
11120 }
11121 .notification_widget.info .badge {
11122 color: #5bc0de;
11123 background-color: #fff;
11124 }
11125 .notification_widget.danger {
11126 color: #fff;
11127 background-color: #d9534f;
11128 border-color: #d43f3a;
11129 }
11130 .notification_widget.danger:focus,
11131 .notification_widget.danger.focus {
11132 color: #fff;
11133 background-color: #c9302c;
11134 border-color: #761c19;
11135 }
11136 .notification_widget.danger:hover {
11137 color: #fff;
11138 background-color: #c9302c;
11139 border-color: #ac2925;
11140 }
11141 .notification_widget.danger:active,
11142 .notification_widget.danger.active,
11143 .open > .dropdown-toggle.notification_widget.danger {
11144 color: #fff;
11145 background-color: #c9302c;
11146 border-color: #ac2925;
11147 }
11148 .notification_widget.danger:active:hover,
11149 .notification_widget.danger.active:hover,
11150 .open > .dropdown-toggle.notification_widget.danger:hover,
11151 .notification_widget.danger:active:focus,
11152 .notification_widget.danger.active:focus,
11153 .open > .dropdown-toggle.notification_widget.danger:focus,
11154 .notification_widget.danger:active.focus,
11155 .notification_widget.danger.active.focus,
11156 .open > .dropdown-toggle.notification_widget.danger.focus {
11157 color: #fff;
11158 background-color: #ac2925;
11159 border-color: #761c19;
11160 }
11161 .notification_widget.danger:active,
11162 .notification_widget.danger.active,
11163 .open > .dropdown-toggle.notification_widget.danger {
11164 background-image: none;
11165 }
11166 .notification_widget.danger.disabled:hover,
11167 .notification_widget.danger[disabled]:hover,
11168 fieldset[disabled] .notification_widget.danger:hover,
11169 .notification_widget.danger.disabled:focus,
11170 .notification_widget.danger[disabled]:focus,
11171 fieldset[disabled] .notification_widget.danger:focus,
11172 .notification_widget.danger.disabled.focus,
11173 .notification_widget.danger[disabled].focus,
11174 fieldset[disabled] .notification_widget.danger.focus {
11175 background-color: #d9534f;
11176 border-color: #d43f3a;
11177 }
11178 .notification_widget.danger .badge {
11179 color: #d9534f;
11180 background-color: #fff;
11181 }
11182 div#pager {
11183 background-color: #fff;
11184 font-size: 14px;
11185 line-height: 20px;
11186 overflow: hidden;
11187 display: none;
11188 position: fixed;
11189 bottom: 0px;
11190 width: 100%;
11191 max-height: 50%;
11192 padding-top: 8px;
11193 -webkit-box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
11194 box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
11195 /* Display over codemirror */
11196 z-index: 100;
11197 /* Hack which prevents jquery ui resizable from changing top. */
11198 top: auto !important;
11199 }
11200 div#pager pre {
11201 line-height: 1.21429em;
11202 color: #000;
11203 background-color: #f7f7f7;
11204 padding: 0.4em;
11205 }
11206 div#pager #pager-button-area {
11207 position: absolute;
11208 top: 8px;
11209 right: 20px;
11210 }
11211 div#pager #pager-contents {
11212 position: relative;
11213 overflow: auto;
11214 width: 100%;
11215 height: 100%;
11216 }
11217 div#pager #pager-contents #pager-container {
11218 position: relative;
11219 padding: 15px 0px;
11220 box-sizing: border-box;
11221 -moz-box-sizing: border-box;
11222 -webkit-box-sizing: border-box;
11223 }
11224 div#pager .ui-resizable-handle {
11225 top: 0px;
11226 height: 8px;
11227 background: #f7f7f7;
11228 border-top: 1px solid #cfcfcf;
11229 border-bottom: 1px solid #cfcfcf;
11230 /* This injects handle bars (a short, wide = symbol) for
11231 the resize handle. */
11232 }
11233 div#pager .ui-resizable-handle::after {
11234 content: '';
11235 top: 2px;
11236 left: 50%;
11237 height: 3px;
11238 width: 30px;
11239 margin-left: -15px;
11240 position: absolute;
11241 border-top: 1px solid #cfcfcf;
11242 }
11243 .quickhelp {
11244 /* Old browsers */
11245 display: -webkit-box;
11246 -webkit-box-orient: horizontal;
11247 -webkit-box-align: stretch;
11248 display: -moz-box;
11249 -moz-box-orient: horizontal;
11250 -moz-box-align: stretch;
11251 display: box;
11252 box-orient: horizontal;
11253 box-align: stretch;
11254 /* Modern browsers */
11255 display: flex;
11256 flex-direction: row;
11257 align-items: stretch;
11258 line-height: 1.8em;
11259 }
11260 .shortcut_key {
11261 display: inline-block;
11262 width: 21ex;
11263 text-align: right;
11264 font-family: monospace;
11265 }
11266 .shortcut_descr {
11267 display: inline-block;
11268 /* Old browsers */
11269 -webkit-box-flex: 1;
11270 -moz-box-flex: 1;
11271 box-flex: 1;
11272 /* Modern browsers */
11273 flex: 1;
11274 }
11275 span.save_widget {
11276 margin-top: 6px;
11277 }
11278 span.save_widget span.filename {
11279 height: 1em;
11280 line-height: 1em;
11281 padding: 3px;
11282 margin-left: 16px;
11283 border: none;
11284 font-size: 146.5%;
11285 border-radius: 2px;
11286 }
11287 span.save_widget span.filename:hover {
11288 background-color: #e6e6e6;
11289 }
11290 span.checkpoint_status,
11291 span.autosave_status {
11292 font-size: small;
11293 }
11294 @media (max-width: 767px) {
11295 span.save_widget {
11296 font-size: small;
11297 }
11298 span.checkpoint_status,
11299 span.autosave_status {
11300 display: none;
11301 }
11302 }
11303 @media (min-width: 768px) and (max-width: 991px) {
11304 span.checkpoint_status {
11305 display: none;
11306 }
11307 span.autosave_status {
11308 font-size: x-small;
11309 }
11310 }
11311 .toolbar {
11312 padding: 0px;
11313 margin-left: -5px;
11314 margin-top: 2px;
11315 margin-bottom: 5px;
11316 box-sizing: border-box;
11317 -moz-box-sizing: border-box;
11318 -webkit-box-sizing: border-box;
11319 }
11320 .toolbar select,
11321 .toolbar label {
11322 width: auto;
11323 vertical-align: middle;
11324 margin-right: 2px;
11325 margin-bottom: 0px;
11326 display: inline;
11327 font-size: 92%;
11328 margin-left: 0.3em;
11329 margin-right: 0.3em;
11330 padding: 0px;
11331 padding-top: 3px;
11332 }
11333 .toolbar .btn {
11334 padding: 2px 8px;
11335 }
11336 .toolbar .btn-group {
11337 margin-top: 0px;
11338 margin-left: 5px;
11339 }
11340 #maintoolbar {
11341 margin-bottom: -3px;
11342 margin-top: -8px;
11343 border: 0px;
11344 min-height: 27px;
11345 margin-left: 0px;
11346 padding-top: 11px;
11347 padding-bottom: 3px;
11348 }
11349 #maintoolbar .navbar-text {
11350 float: none;
11351 vertical-align: middle;
11352 text-align: right;
11353 margin-left: 5px;
11354 margin-right: 0px;
11355 margin-top: 0px;
11356 }
11357 .select-xs {
11358 height: 24px;
11359 }
11360 .pulse,
11361 .dropdown-menu > li > a.pulse,
11362 li.pulse > a.dropdown-toggle,
11363 li.pulse.open > a.dropdown-toggle {
11364 background-color: #F37626;
11365 color: white;
11366 }
11367 /**
11368 * Primary styles
11369 *
11370 * Author: Jupyter Development Team
11371 */
11372 /** WARNING IF YOU ARE EDITTING THIS FILE, if this is a .css file, It has a lot
11373 * of chance of beeing generated from the ../less/[samename].less file, you can
11374 * try to get back the less file by reverting somme commit in history
11375 **/
11376 /*
11377 * We'll try to get something pretty, so we
11378 * have some strange css to have the scroll bar on
11379 * the left with fix button on the top right of the tooltip
11380 */
11381 @-moz-keyframes fadeOut {
11382 from {
11383 opacity: 1;
11384 }
11385 to {
11386 opacity: 0;
11387 }
11388 }
11389 @-webkit-keyframes fadeOut {
11390 from {
11391 opacity: 1;
11392 }
11393 to {
11394 opacity: 0;
11395 }
11396 }
11397 @-moz-keyframes fadeIn {
11398 from {
11399 opacity: 0;
11400 }
11401 to {
11402 opacity: 1;
11403 }
11404 }
11405 @-webkit-keyframes fadeIn {
11406 from {
11407 opacity: 0;
11408 }
11409 to {
11410 opacity: 1;
11411 }
11412 }
11413 /*properties of tooltip after "expand"*/
11414 .bigtooltip {
11415 overflow: auto;
11416 height: 200px;
11417 -webkit-transition-property: height;
11418 -webkit-transition-duration: 500ms;
11419 -moz-transition-property: height;
11420 -moz-transition-duration: 500ms;
11421 transition-property: height;
11422 transition-duration: 500ms;
11423 }
11424 /*properties of tooltip before "expand"*/
11425 .smalltooltip {
11426 -webkit-transition-property: height;
11427 -webkit-transition-duration: 500ms;
11428 -moz-transition-property: height;
11429 -moz-transition-duration: 500ms;
11430 transition-property: height;
11431 transition-duration: 500ms;
11432 text-overflow: ellipsis;
11433 overflow: hidden;
11434 height: 80px;
11435 }
11436 .tooltipbuttons {
11437 position: absolute;
11438 padding-right: 15px;
11439 top: 0px;
11440 right: 0px;
11441 }
11442 .tooltiptext {
11443 /*avoid the button to overlap on some docstring*/
11444 padding-right: 30px;
11445 }
11446 .ipython_tooltip {
11447 max-width: 700px;
11448 /*fade-in animation when inserted*/
11449 -webkit-animation: fadeOut 400ms;
11450 -moz-animation: fadeOut 400ms;
11451 animation: fadeOut 400ms;
11452 -webkit-animation: fadeIn 400ms;
11453 -moz-animation: fadeIn 400ms;
11454 animation: fadeIn 400ms;
11455 vertical-align: middle;
11456 background-color: #f7f7f7;
11457 overflow: visible;
11458 border: #ababab 1px solid;
11459 outline: none;
11460 padding: 3px;
11461 margin: 0px;
11462 padding-left: 7px;
11463 font-family: monospace;
11464 min-height: 50px;
11465 -moz-box-shadow: 0px 6px 10px -1px #adadad;
11466 -webkit-box-shadow: 0px 6px 10px -1px #adadad;
11467 box-shadow: 0px 6px 10px -1px #adadad;
11468 border-radius: 2px;
11469 position: absolute;
11470 z-index: 1000;
11471 }
11472 .ipython_tooltip a {
11473 float: right;
11474 }
11475 .ipython_tooltip .tooltiptext pre {
11476 border: 0;
11477 border-radius: 0;
11478 font-size: 100%;
11479 background-color: #f7f7f7;
11480 }
11481 .pretooltiparrow {
11482 left: 0px;
11483 margin: 0px;
11484 top: -16px;
11485 width: 40px;
11486 height: 16px;
11487 overflow: hidden;
11488 position: absolute;
11489 }
11490 .pretooltiparrow:before {
11491 background-color: #f7f7f7;
11492 border: 1px #ababab solid;
11493 z-index: 11;
11494 content: "";
11495 position: absolute;
11496 left: 15px;
11497 top: 10px;
11498 width: 25px;
11499 height: 25px;
11500 -webkit-transform: rotate(45deg);
11501 -moz-transform: rotate(45deg);
11502 -ms-transform: rotate(45deg);
11503 -o-transform: rotate(45deg);
11504 }
11505 ul.typeahead-list i {
11506 margin-left: -10px;
11507 width: 18px;
11508 }
11509 ul.typeahead-list {
11510 max-height: 80vh;
11511 overflow: auto;
11512 }
11513 ul.typeahead-list > li > a {
11514 /** Firefox bug **/
11515 /* see https://github.com/jupyter/notebook/issues/559 */
11516 white-space: normal;
11517 }
11518 .cmd-palette .modal-body {
11519 padding: 7px;
11520 }
11521 .cmd-palette form {
11522 background: white;
11523 }
11524 .cmd-palette input {
11525 outline: none;
11526 }
11527 .no-shortcut {
11528 display: none;
11529 }
11530 .command-shortcut:before {
11531 content: "(command)";
11532 padding-right: 3px;
11533 color: #777777;
11534 }
11535 .edit-shortcut:before {
11536 content: "(edit)";
11537 padding-right: 3px;
11538 color: #777777;
11539 }
11540 #find-and-replace #replace-preview .match,
11541 #find-and-replace #replace-preview .insert {
11542 background-color: #BBDEFB;
11543 border-color: #90CAF9;
11544 border-style: solid;
11545 border-width: 1px;
11546 border-radius: 0px;
11547 }
11548 #find-and-replace #replace-preview .replace .match {
11549 background-color: #FFCDD2;
11550 border-color: #EF9A9A;
11551 border-radius: 0px;
11552 }
11553 #find-and-replace #replace-preview .replace .insert {
11554 background-color: #C8E6C9;
11555 border-color: #A5D6A7;
11556 border-radius: 0px;
11557 }
11558 #find-and-replace #replace-preview {
11559 max-height: 60vh;
11560 overflow: auto;
11561 }
11562 #find-and-replace #replace-preview pre {
11563 padding: 5px 10px;
11564 }
11565 .terminal-app {
11566 background: #EEE;
11567 }
11568 .terminal-app #header {
11569 background: #fff;
11570 -webkit-box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
11571 box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.2);
11572 }
11573 .terminal-app .terminal {
11574 width: 100%;
11575 float: left;
11576 font-family: monospace;
11577 color: white;
11578 background: black;
11579 padding: 0.4em;
11580 border-radius: 2px;
11581 -webkit-box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.4);
11582 box-shadow: 0px 0px 12px 1px rgba(87, 87, 87, 0.4);
11583 }
11584 .terminal-app .terminal,
11585 .terminal-app .terminal dummy-screen {
11586 line-height: 1em;
11587 font-size: 14px;
11588 }
11589 .terminal-app .terminal .xterm-rows {
11590 padding: 10px;
11591 }
11592 .terminal-app .terminal-cursor {
11593 color: black;
11594 background: white;
11595 }
11596 .terminal-app #terminado-container {
11597 margin-top: 20px;
11598 }
11599 /*# sourceMappingURL=style.min.css.map */
11600 .c-ElasticMatch { background-color: #faffa6; padding: 0.2em;}
11601 .hll { background-color: #ffffcc }
11602 .c { color: #408080; font-style: italic } /* Comment */
11603 .err, .codehilite .err { border: none } /* Error */
11604 .k { color: #008000; font-weight: bold } /* Keyword */
11605 .o { color: #666666 } /* Operator */
11606 .ch { color: #408080; font-style: italic } /* Comment.Hashbang */
11607 .cm { color: #408080; font-style: italic } /* Comment.Multiline */
11608 .cp { color: #BC7A00 } /* Comment.Preproc */
11609 .cpf { color: #408080; font-style: italic } /* Comment.PreprocFile */
11610 .c1 { color: #408080; font-style: italic } /* Comment.Single */
11611 .cs { color: #408080; font-style: italic } /* Comment.Special */
11612 .gd { color: #A00000 } /* Generic.Deleted */
11613 .ge { font-style: italic } /* Generic.Emph */
11614 .gr { color: #FF0000 } /* Generic.Error */
11615 .gh { color: #000080; font-weight: bold } /* Generic.Heading */
11616 .gi { color: #00A000 } /* Generic.Inserted */
11617 .go { color: #888888 } /* Generic.Output */
11618 .gp { color: #000080; font-weight: bold } /* Generic.Prompt */
11619 .gs { font-weight: bold } /* Generic.Strong */
11620 .gu { color: #800080; font-weight: bold } /* Generic.Subheading */
11621 .gt { color: #0044DD } /* Generic.Traceback */
11622 .kc { color: #008000; font-weight: bold } /* Keyword.Constant */
11623 .kd { color: #008000; font-weight: bold } /* Keyword.Declaration */
11624 .kn { color: #008000; font-weight: bold } /* Keyword.Namespace */
11625 .kp { color: #008000 } /* Keyword.Pseudo */
11626 .kr { color: #008000; font-weight: bold } /* Keyword.Reserved */
11627 .kt { color: #B00040 } /* Keyword.Type */
11628 .m { color: #666666 } /* Literal.Number */
11629 .s { color: #BA2121 } /* Literal.String */
11630 .na { color: #7D9029 } /* Name.Attribute */
11631 .nb { color: #008000 } /* Name.Builtin */
11632 .nc { color: #0000FF; font-weight: bold } /* Name.Class */
11633 .no { color: #880000 } /* Name.Constant */
11634 .nd { color: #AA22FF } /* Name.Decorator */
11635 .ni { color: #999999; font-weight: bold } /* Name.Entity */
11636 .ne { color: #D2413A; font-weight: bold } /* Name.Exception */
11637 .nf { color: #0000FF } /* Name.Function */
11638 .nl { color: #A0A000 } /* Name.Label */
11639 .nn { color: #0000FF; font-weight: bold } /* Name.Namespace */
11640 .nt { color: #008000; font-weight: bold } /* Name.Tag */
11641 .nv { color: #19177C } /* Name.Variable */
11642 .ow { color: #AA22FF; font-weight: bold } /* Operator.Word */
11643 .w { color: #bbbbbb } /* Text.Whitespace */
11644 .mb { color: #666666 } /* Literal.Number.Bin */
11645 .mf { color: #666666 } /* Literal.Number.Float */
11646 .mh { color: #666666 } /* Literal.Number.Hex */
11647 .mi { color: #666666 } /* Literal.Number.Integer */
11648 .mo { color: #666666 } /* Literal.Number.Oct */
11649 .sa { color: #BA2121 } /* Literal.String.Affix */
11650 .sb { color: #BA2121 } /* Literal.String.Backtick */
11651 .sc { color: #BA2121 } /* Literal.String.Char */
11652 .dl { color: #BA2121 } /* Literal.String.Delimiter */
11653 .sd { color: #BA2121; font-style: italic } /* Literal.String.Doc */
11654 .s2 { color: #BA2121 } /* Literal.String.Double */
11655 .se { color: #BB6622; font-weight: bold } /* Literal.String.Escape */
11656 .sh { color: #BA2121 } /* Literal.String.Heredoc */
11657 .si { color: #BB6688; font-weight: bold } /* Literal.String.Interpol */
11658 .sx { color: #008000 } /* Literal.String.Other */
11659 .sr { color: #BB6688 } /* Literal.String.Regex */
11660 .s1 { color: #BA2121 } /* Literal.String.Single */
11661 .ss { color: #19177C } /* Literal.String.Symbol */
11662 .bp { color: #008000 } /* Name.Builtin.Pseudo */
11663 .fm { color: #0000FF } /* Name.Function.Magic */
11664 .vc { color: #19177C } /* Name.Variable.Class */
11665 .vg { color: #19177C } /* Name.Variable.Global */
11666 .vi { color: #19177C } /* Name.Variable.Instance */
11667 .vm { color: #19177C } /* Name.Variable.Magic */
11668 .il { color: #666666 } /* Literal.Number.Integer.Long */
11669 } No newline at end of file
This diff has been collapsed as it changes many lines, (623 lines changed) Show them Hide them
@@ -0,0 +1,623 b''
1 {
2 "name": "rcicons",
3 "css_prefix_text": "icon-",
4 "css_use_suffix": false,
5 "hinting": true,
6 "units_per_em": 1000,
7 "ascent": 850,
8 "copyright": "RhodeCode GmbH",
9 "glyphs": [
10 {
11 "uid": "a5f9b6d4d795603e6e29a5b8007cc139",
12 "css": "bookmark",
13 "code": 59395,
14 "src": "custom_icons",
15 "selected": true,
16 "svg": {
17 "path": "M780 990L520 700C510 690 495 690 485 700L225 995C205 1015 180 1000 180 965V35C175 15 190 0 205 0H795C810 0 825 15 825 35V960C825 995 795 1010 780 990Z",
18 "width": 1000
19 },
20 "search": [
21 "bookmark"
22 ]
23 },
24 {
25 "uid": "fbc028d3a6a0df72f8f508ff5dfbab72",
26 "css": "tag",
27 "code": 59397,
28 "src": "custom_icons",
29 "selected": true,
30 "svg": {
31 "path": "M459.8 62.5L93.8 53.6C75.9 53.6 62.5 67 62.5 84.8L75.9 450.9C75.9 459.8 80.4 464.3 84.8 473.2L549.1 937.5C562.5 950.9 580.4 950.9 593.8 937.5L946.4 584.8C959.8 571.4 959.8 553.6 946.4 540.2L477.7 71.4C473.2 67 464.3 62.5 459.8 62.5ZM357.1 285.7C357.1 321.4 325.9 352.7 290.2 352.7 254.5 352.7 223.2 321.4 223.2 285.7 223.2 250 254.5 218.8 290.2 218.8S357.1 245.5 357.1 285.7Z",
32 "width": 1000
33 },
34 "search": [
35 "tag"
36 ]
37 },
38 {
39 "uid": "1c67c02366438b324c184ff9e356dca1",
40 "css": "branch",
41 "code": 59396,
42 "src": "custom_icons",
43 "selected": true,
44 "svg": {
45 "path": "M875 250C875 174.1 817 116.1 741.1 116.1S607.1 174.1 607.1 250C607.1 299.1 633.9 339.3 669.6 361.6 651.8 504.5 531.3 544.6 459.8 558V245.5C504.5 223.2 531.3 183 531.3 133.9 531.3 58 473.2 0 397.3 0S263.4 58 263.4 133.9C263.4 183 290.2 227.7 330.4 250V750C290.2 772.3 263.4 817 263.4 866.1 263.4 942 321.4 1000 397.3 1000S531.3 942 531.3 866.1C531.3 817 504.5 772.3 464.3 750V692C526.8 683 629.5 660.7 709.8 580.4 767.9 522.3 799.1 450.9 808 366.1 848.2 343.8 875 299.1 875 250ZM397.3 89.3C424.1 89.3 442 107.1 442 133.9S424.1 178.6 397.3 178.6 352.7 160.7 352.7 133.9 370.5 89.3 397.3 89.3ZM397.3 910.7C370.5 910.7 352.7 892.9 352.7 866.1S370.5 821.4 397.3 821.4 442 839.3 442 866.1 419.6 910.7 397.3 910.7ZM741.1 205.4C767.9 205.4 785.7 223.2 785.7 250S767.9 294.6 741.1 294.6 696.4 276.8 696.4 250 718.8 205.4 741.1 205.4Z",
46 "width": 1000
47 },
48 "search": [
49 "branch"
50 ]
51 },
52 {
53 "uid": "b75f7b47706aebd803ef370082e8e334",
54 "css": "group",
55 "code": 59407,
56 "src": "custom_icons",
57 "selected": true,
58 "svg": {
59 "path": "M961.5 630.8V646.2C961.5 650 957.7 657.7 950 657.7H788.5 784.6C769.2 638.5 746.2 619.2 707.7 615.4 673.1 607.7 653.8 600 638.5 592.3 646.2 584.6 657.7 580.8 669.2 576.9 715.4 569.2 726.9 553.8 734.6 542.3 742.3 530.8 742.3 519.2 734.6 503.8 726.9 488.5 703.8 461.5 703.8 423.1 703.8 384.6 703.8 319.2 776.9 319.2H784.6 792.3C865.4 323.1 869.2 384.6 865.4 423.1 865.4 461.5 842.3 492.3 834.6 503.8 826.9 519.2 826.9 530.8 834.6 542.3 842.3 553.8 857.7 569.2 900 576.9 953.8 580.8 961.5 623.1 961.5 630.8 961.5 630.8 961.5 630.8 961.5 630.8ZM253.8 646.2C269.2 630.8 292.3 615.4 323.1 611.5 361.5 603.8 384.6 596.2 396.2 584.6 388.5 576.9 376.9 569.2 361.5 565.4 315.4 557.7 303.8 542.3 296.2 530.8 288.5 519.2 288.5 507.7 296.2 492.3 303.8 476.9 326.9 450 326.9 411.5 326.9 373.1 326.9 307.7 253.8 307.7H246.2 234.6C161.5 311.5 157.7 373.1 161.5 411.5 161.5 450 184.6 480.8 192.3 492.3 200 507.7 200 519.2 192.3 530.8 184.6 542.3 169.2 557.7 126.9 565.4 80.8 573.1 73.1 615.4 73.1 619.2 73.1 619.2 73.1 619.2 73.1 619.2V634.6C73.1 638.5 76.9 646.2 84.6 646.2H246.2 253.8ZM707.7 634.6C634.6 623.1 611.5 600 600 580.8 588.5 561.5 588.5 542.3 600 519.2 611.5 496.2 650 450 653.8 388.5 657.7 326.9 653.8 223.1 534.6 219.2H519.2 503.8C384.6 223.1 380.8 323.1 384.6 384.6 388.5 446.2 423.1 492.3 438.5 515.4 450 538.5 450 557.7 438.5 576.9 426.9 596.2 403.8 619.2 330.8 630.8 257.7 642.3 246.2 711.5 246.2 719.2 246.2 719.2 246.2 719.2 246.2 719.2V742.3C246.2 750 253.8 757.7 261.5 757.7H519.2 776.9C784.6 757.7 792.3 750 792.3 742.3V719.2C792.3 719.2 792.3 719.2 792.3 719.2 788.5 715.4 780.8 646.2 707.7 634.6Z",
60 "width": 1000
61 },
62 "search": [
63 "group"
64 ]
65 },
66 {
67 "uid": "7ae0ef039bb0217d9581e44b09448905",
68 "css": "fork",
69 "code": 59409,
70 "src": "custom_icons",
71 "selected": true,
72 "svg": {
73 "path": "M792.3 196.2C792.3 138.5 746.2 96.2 692.3 96.2 634.6 96.2 592.3 142.3 592.3 196.2 592.3 230.8 611.5 261.5 638.5 280.8 626.9 365.4 569.2 403.8 511.5 423.1 453.8 407.7 396.2 369.2 384.6 280.8 411.5 261.5 430.8 230.8 430.8 196.2 430.8 138.5 384.6 96.2 330.8 96.2S223.1 138.5 223.1 196.2C223.1 234.6 246.2 269.2 276.9 284.6 288.5 392.3 353.8 473.1 457.7 511.5V673.1C426.9 692.3 407.7 723.1 407.7 761.5 407.7 819.2 453.8 861.5 507.7 861.5S607.7 815.4 607.7 761.5C607.7 723.1 588.5 692.3 557.7 673.1V511.5C661.5 473.1 726.9 392.3 738.5 284.6 769.2 265.4 792.3 234.6 792.3 196.2ZM326.9 161.5C346.2 161.5 361.5 176.9 361.5 196.2S346.2 226.9 326.9 226.9 292.3 215.4 292.3 196.2 307.7 161.5 326.9 161.5ZM507.7 796.2C488.5 796.2 473.1 780.8 473.1 761.5S488.5 726.9 507.7 726.9C526.9 726.9 542.3 742.3 542.3 761.5S526.9 796.2 507.7 796.2ZM692.3 161.5C711.5 161.5 726.9 176.9 726.9 196.2S711.5 226.9 692.3 226.9 657.7 211.5 657.7 192.3 673.1 161.5 692.3 161.5Z",
74 "width": 1000
75 },
76 "search": [
77 "fork"
78 ]
79 },
80 {
81 "uid": "65e66c3e7d74e2c345fb78fadd400d3f",
82 "css": "rhodecode",
83 "code": 59441,
84 "src": "custom_icons",
85 "selected": true,
86 "svg": {
87 "path": "M174.6 216.8C173.4 220.9 172.2 225 171 229.1 168.1 239.1 165.2 249.1 162.3 259.1 158.7 271.6 155 284.2 151.4 296.7 148 308.4 144.6 320.1 141.2 331.8 139 339.3 136.8 346.8 134.7 354.3 134.4 355.4 134.1 356.5 133.7 357.6 133.7 357.7 133.9 358.2 134 358.3 134.3 359 134.5 359.7 134.8 360.5 137.2 367.3 139.7 374.1 142.1 381 146 392 149.9 403 153.9 414.1 158.3 426.5 162.8 439 167.2 451.4 171.1 462.5 175.1 473.6 179 484.7 181.5 491.7 184 498.6 186.4 505.6 186.8 506.7 187.2 507.7 187.5 508.8 187.8 509.6 188.6 510.4 189 511.1 192.8 516.9 196.5 522.6 200.3 528.4 206.5 537.9 212.7 547.4 219 556.9 226.2 567.9 233.4 578.9 240.6 590 247.3 600.3 254.1 610.6 260.8 620.9 265.6 628.2 270.4 635.6 275.2 642.9 276.4 644.8 277.6 646.6 278.9 648.5 279.2 649 279.5 649.5 279.8 649.8 282.7 652.6 285.5 655.4 288.4 658.2 294.6 664.3 300.9 670.5 307.1 676.6 315.5 684.9 323.9 693.2 332.4 701.4 341.8 710.6 351.2 719.9 360.6 729.1 369.8 738.1 378.9 747.1 388.1 756.1 395.8 763.7 403.6 771.3 411.3 778.9 416.4 783.9 421.5 788.9 426.6 793.9 428.2 795.5 429.8 797.3 431.6 798.6 438.9 803.9 446.1 809.2 453.4 814.5 463.7 822 473.9 829.5 484.2 837 487.6 839.5 491.1 842 494.5 844.5 495.3 845.1 496.1 845.7 496.9 846.3 497.2 846.5 497.2 846.6 497.6 846.4 504.7 842.7 511.8 839.1 518.9 835.4 530.3 829.5 541.7 823.6 553.1 817.7 559.2 814.5 565.4 811.4 571.5 808.2 571.9 808 572.3 807.1 572.6 806.8 573.7 805.4 574.8 804 576 802.5 580.2 797.2 584.3 791.9 588.5 786.7 594.7 778.9 600.8 771.1 607 763.3 614.5 753.8 622 744.3 629.5 734.8 637.7 724.5 645.8 714.1 654 703.8 662.1 693.5 670.3 683.2 678.4 672.9 685.9 663.5 693.3 654 700.8 644.6 706.9 636.9 713 629.2 719.1 621.5 723.2 616.4 727.2 611.2 731.3 606.1 732.7 604.4 734 602.6 735.4 600.9 735.2 600.8 734.8 600.8 734.6 600.7 733.8 600.5 733 600.4 732.2 600.2 729.1 599.6 726 598.9 722.9 598.2 718 597.1 713 596 708.1 594.8 701.5 593.2 694.9 591.5 688.3 589.7 680.2 587.5 672.2 585.2 664.1 582.9 654.7 580.1 645.4 577.2 636.1 574.1 625.6 570.6 615.2 567 604.8 563.3 593.4 559.1 582 554.8 570.8 550.2 558.6 545.3 546.6 540.1 534.6 534.8 521.9 529.1 509.3 523.1 496.8 516.8 483.7 510.2 470.7 503.4 457.9 496.2 444.6 488.7 431.4 480.9 418.5 472.8 405.1 464.4 392 455.6 379.1 446.4 365.9 437 352.9 427.1 340.3 416.9 327.4 406.4 314.8 395.5 302.7 384.2 290.3 372.6 278.3 360.6 266.8 348.1 255.1 335.3 243.8 322.1 233.2 308.4 222.3 294.4 212 279.9 202.4 265 192.5 249.7 183.4 233.9 175 217.8 175 217.4 174.8 217.1 174.6 216.8ZM172.1 214.2C170.7 218.7 169.3 223.3 167.8 227.8 164.5 238.5 161.1 249.2 157.8 259.9 153.9 272.4 150 285 146.1 297.5 143 307.5 139.9 317.4 136.7 327.4 135.9 330.1 135 332.7 134.2 335.4 134 336.1 133.6 336.7 133.8 337.4 135.4 342.2 137 347.1 138.6 351.9 141.9 361.9 145.2 371.8 148.6 381.8 152.7 394.1 156.8 406.5 160.9 418.8 164.9 430.8 168.9 442.8 172.9 454.8 175.9 463.7 178.8 472.6 181.8 481.4 182.6 483.8 183.4 486.2 184.2 488.7 184.4 489.4 184.6 490.1 184.9 490.8 187.2 495 189.5 499.2 191.8 503.4 196.8 512.6 201.9 521.8 206.9 531 213.2 542.4 219.4 553.9 225.7 565.3 231.7 576.2 237.6 587.1 243.6 598 247.8 605.6 251.9 613.2 256.1 620.8 257.3 623 258.2 625.4 259.9 627.2 264.1 631.7 268.3 636.2 272.5 640.7 280.2 648.9 287.9 657.2 295.5 665.4 304.5 675 313.5 684.7 322.4 694.3 330.5 703 338.6 711.7 346.7 720.4 351.8 725.8 356.8 731.3 361.9 736.7 363.5 738.4 365 740 366.6 741.6 372.3 747.3 378 753 383.7 758.7 392.5 767.5 401.2 776.2 410 785 419.1 794.1 428.3 803.3 437.4 812.4 444.2 819.2 451.1 826.1 457.9 832.9 459.6 834.6 461.3 836.3 463 838 463.3 838.3 463.6 838.6 463.8 838.8 463.9 838.9 465.1 838.7 465.3 838.6 475.9 837.2 486.5 835.8 497 834.5 505.6 833.4 514.1 832.3 522.7 831.2 523 831.2 523.7 830.1 523.9 829.9 525.1 828.6 526.3 827.2 527.6 825.9 532.1 820.9 536.7 815.9 541.2 810.9 547.9 803.5 554.6 796.1 561.4 788.7 569.6 779.7 577.7 770.7 585.9 761.8 594.8 752 603.6 742.3 612.5 732.5 621.3 722.8 630.1 713.1 639 703.4 647 694.5 655.1 685.7 663.1 676.8 669.6 669.6 676.2 662.4 682.7 655.2 687 650.5 691.3 645.8 695.6 641 696.6 639.9 697.7 638.7 698.7 637.6 698.9 637.4 699.6 636.9 699.6 636.6 699.6 636.5 696.6 635.7 696.5 635.7 693.5 634.8 690.4 633.9 687.4 633 682.6 631.5 677.8 630 673 628.4 666.6 626.3 660.1 624.1 653.8 621.8 645.9 619 638.1 616.1 630.3 613.1 621.2 609.6 612.1 606 603.1 602.2 592.9 598 582.8 593.6 572.8 589 561.8 584 550.8 578.8 540 573.4 528.3 567.6 516.7 561.6 505.2 555.3 493 548.7 480.9 541.8 469 534.6 456.5 527.1 444.1 519.3 431.9 511.2 419.2 502.8 406.7 494 394.5 484.9 381.8 475.5 369.5 465.8 357.4 455.7 345 445.3 332.8 434.6 321.1 423.4 309.1 412 297.4 400.2 286.2 388 274.7 375.5 263.7 362.6 253.2 349.3 242.5 335.7 232.3 321.7 222.8 307.2 213 292.4 203.9 277.2 195.5 261.7 186.8 246.5 179 230.5 172.1 214.2ZM169.5 204C168.8 207.8 168.1 211.6 167.3 215.4 165.5 224.9 163.7 234.5 161.9 244 159.5 256.5 157.1 269 154.7 281.5 152.3 294.2 149.8 307 147.4 319.7 145.5 329.9 143.5 340.1 141.6 350.3 140.7 355.2 139.7 360.1 138.8 365 138.7 365.7 139.1 366.4 139.3 367 140.2 369.6 141.1 372.2 142 374.8 145.4 384.5 148.7 394.3 152.1 404 156.4 416.4 160.7 428.7 165 441.1 168.8 452.1 172.6 463 176.4 474 178.3 479.5 180.2 485 182.1 490.5 182.3 491.2 182.7 491.8 183 492.4 184.2 494.8 185.4 497.1 186.5 499.5 190.9 508.4 195.4 517.2 199.8 526.1 205.6 537.7 211.4 549.3 217.2 560.9 222.7 571.9 228.2 583 233.8 594 237.4 601.2 241 608.3 244.6 615.5 245.2 616.6 245.7 617.7 246.3 618.8 246.7 619.6 247.6 620.4 248.2 621.1 252.8 626.6 257.4 632.1 262 637.7 269.5 646.7 276.9 655.6 284.4 664.6 292.8 674.7 301.3 684.9 309.7 695 317.2 704 324.8 713.1 332.3 722.1 337 727.8 341.8 733.5 346.5 739.1 347.2 740 347.9 740.8 348.7 741.7 348.9 741.9 349.2 742 349.4 742.2 350.2 742.7 350.9 743.2 351.7 743.7 358.7 748.5 365.8 753.3 372.8 758.1 383.3 765.3 393.9 772.5 404.4 779.7 414.6 786.6 424.7 793.6 434.9 800.5 440.8 804.5 446.7 808.6 452.7 812.6 456.3 815.1 459.5 818.1 462.9 820.8 472.5 828.7 482.1 836.7 491.7 844.6 498.5 850.2 505.4 855.9 512.2 861.5 512.8 862 512.7 861.9 513.3 861.3 514.2 860.3 515.2 859.2 516.1 858.2 520 853.9 524 849.6 527.9 845.3 534 838.6 540.2 831.9 546.3 825.2 554 816.8 561.7 808.3 569.4 799.9 578.1 790.4 586.7 781 595.4 771.5 604.4 761.7 613.3 751.9 622.3 742.1 630.9 732.6 639.6 723.2 648.2 713.7 655.9 705.3 663.6 696.9 671.3 688.5 677.4 681.8 683.5 675.1 689.6 668.4 693.5 664.1 697.4 659.9 701.3 655.6 702.4 654.4 703.5 653.2 704.6 652 704.6 652 704.6 652 704.6 652 704.6 652 704.6 652 704.6 652 704.6 652.1 701.6 651.3 701.5 651.3 698.5 650.5 695.5 649.5 692.6 648.6 687.9 647.1 683.1 645.5 678.4 643.8 672.1 641.6 665.8 639.2 659.5 636.9 651.8 634 644.1 630.9 636.4 627.8 627.5 624.1 618.6 620.3 609.7 616.4 599.7 612 589.8 607.4 580 602.7 569.2 597.5 558.4 592.1 547.7 586.6 536.2 580.6 524.8 574.4 513.4 568 501.4 561.2 489.5 554.2 477.7 546.9 465.3 539.3 453.1 531.4 441.1 523.3 428.6 514.8 416.3 506.1 404.2 497 391.7 487.7 379.5 478 367.5 468 355.2 457.8 343.2 447.2 331.5 436.3 319.6 425.2 308 413.6 296.8 401.7 285.4 389.6 274.5 377.1 264 364.3 253.3 351.2 243.2 337.8 233.6 323.9 223.8 309.8 214.6 295.4 206.1 280.5 197.4 265.4 189.4 249.9 182.1 234 177.7 224.2 173.5 214.2 169.5 204ZM866 183.5C863.9 179.4 861.1 176.2 857.1 174 851.9 171.1 846.2 168.9 840.7 166.5 829.5 161.7 818.2 157.4 806.7 153.4 783.6 145.4 760 138.9 736.3 132.9 711.7 126.7 687.1 120.9 662.3 115.7 637.1 110.4 611.7 105.6 586.3 101.4 561.2 97.2 536 93.1 510.5 91.1 497.8 90.1 485 89.9 472.4 91.3 465.9 92 459.4 93.2 453 94.2 446.6 95.2 440.1 96.2 433.7 97.3 408.2 101.5 382.8 106 357.4 111 332.2 115.9 307.1 121.2 282.1 126.9 257.2 132.5 232.6 139.2 208.4 147.3 196.3 151.4 184.2 155.8 172.3 160.5 166.4 162.8 160.5 165.2 154.6 167.7 151.7 168.9 148.8 170.2 145.8 171.4 143.2 172.5 140.6 173.5 138.1 174.7 134 176.7 130.6 179.7 128.3 183.6 127 185.8 126.2 188.2 125.3 190.6 124.2 193.6 123.1 196.6 122.1 199.6 118.1 211.5 114.9 223.7 112.5 236 107.7 260.4 106 285.4 106.8 310.2 107.2 322.7 108.2 335.3 109.7 347.7 111.2 360.2 112.7 372.8 115.1 385.2 119.8 410.4 126.7 435.1 134.8 459.3 138.9 471.4 143.3 483.5 147.9 495.4 152.2 506.5 157.5 517.3 162.7 528 173 549.2 184.4 569.8 196.6 589.9 208.8 609.9 221.9 629.3 235.7 648.1 249.5 666.8 264.1 685 279.3 702.6 295.3 721.1 311.7 739.2 328.6 756.9 345.6 774.8 363 792.2 381 809 398.9 825.9 417.4 842.2 436.4 857.8 445.6 865.4 454.9 872.8 464.2 880.2 473.6 887.7 483.1 895.1 492 903.2 494.3 905.2 496.5 907.3 498.7 909.5 498.9 909.7 499.7 910.8 500 910.8 500.2 910.8 500.5 910.8 500.7 910.8 501.2 910.8 502 911 502.5 910.8 507.3 907.1 512 903.3 516.8 899.6 526.2 892.1 535.6 884.6 544.9 876.9 563.3 861.7 581.4 846.2 599.2 830.3 616.9 814.5 634.1 798.2 651 781.5 667.9 764.7 684.4 747.5 700.3 729.7 716.3 711.8 731.8 693.4 746.5 674.4 761 655.7 774.8 636.5 787.8 616.8 800.7 597.2 812.8 577 823.8 556.2 835 535.1 845.2 513.5 854.3 491.4 863.4 469.1 871.2 446.3 877.3 423 883.4 399.9 887.8 376.4 890.3 352.7 892.9 328.6 893.4 304.3 892 280 891.8 276.9 891 273.8 890.3 270.7 889.7 267.7 889 264.6 888.4 261.6 887.2 255.7 886 249.9 884.7 244 882.3 233 879.7 222 876.5 211.1 873.4 201.8 870.1 192.5 866 183.5 863.5 178.4 878.8 211.7 866 183.5ZM814.8 393.5C808.1 418.2 799.5 442.5 789.4 466 780 487.9 770 509.6 758.5 530.5 747.4 550.7 735.1 570.3 722 589.3 708.8 608.4 694.7 626.8 680 644.8 664.8 663.4 649 681.5 632.7 699.1 615.9 717.3 598.5 734.9 580.5 752 562.5 769.1 544.1 785.7 525.1 801.6 515.7 809.5 506.1 817.3 496.5 824.9 496.1 825.2 495.2 826.3 494.7 826.3 494 826.3 493.3 826.3 492.6 826.3 492 826.3 491.4 825.5 491 825.1 490.5 824.6 490 824.1 489.5 823.6 488.4 822.6 487.2 821.5 486.1 820.5 481.6 816.6 476.9 813.1 472.2 809.4 469.9 807.6 467.6 805.7 465.3 803.8 463.1 801.9 461 799.8 458.8 797.8 454.2 793.7 449.7 789.6 445.2 785.5 435.9 777 426.6 768.5 417.5 759.8 408.4 751.1 399.5 742.3 390.9 733.2 386.7 728.8 382.7 724.3 378.4 720 374.2 715.8 370 711.5 365.8 707.2 349.1 690 332.9 672.5 317.4 654.3 301.8 636 286.9 617 273.1 597.3 259.2 577.5 246.4 556.9 234.5 535.8 222.8 515 212.1 493.7 202.6 471.8 193.1 449.9 184.8 427.4 177.9 404.6 176.1 398.6 174.4 392.6 173.1 386.5 171.7 380.1 170.6 373.6 169.6 367.1 167.6 354.2 166.3 341.2 165.5 328.2 164.7 315.3 164.3 302.3 164.5 289.3 164.7 276.7 165.9 264.2 167.5 251.7 167.9 248.5 168.3 245.4 168.7 242.2 168.9 240.6 169.1 239.1 169.3 237.5 169.5 235.9 169.6 234.3 169.8 232.7 170.1 230.3 171.1 228.1 171.7 225.7 172 224.5 172.2 223.2 172.2 221.9 172.2 220.8 172.8 220.1 173.6 219.5 174.6 218.8 175.6 218.3 176.5 217.5 177.1 217 177.6 216.6 178.4 216.3 179.2 216 180.1 215.7 180.9 215.3 183.9 214.2 186.8 213 189.8 211.9 195.7 209.7 201.6 207.5 207.6 205.3 231.3 196.7 255.3 189 279.7 182.4 292 179.1 304.3 176.1 316.7 173.5 322.9 172.2 329.1 170.6 335.4 169.3 341.7 167.9 348 166.6 354.3 165.4 379.8 160.4 405.4 156.3 431.1 152.5 444 150.6 457 148.8 470 147 473.2 146.6 476.5 146.1 479.7 145.7 481.3 145.5 482.8 145.3 484.4 145.1 485.7 144.9 487.1 145 488.4 145.1 493.9 145.1 499.5 145.3 504.9 146.3 506.2 146.5 507.4 146.8 508.6 147.1 510.1 147.5 511.5 147.8 513 148 516.1 148.4 519.2 148.9 522.3 149.3 528.6 150.2 534.8 151.1 541.1 152 553.7 153.8 566.4 155.7 579 157.7 604.4 161.7 629.7 166 654.8 171.4 680 176.8 705 183.2 729.7 190.3 742.1 193.9 754.4 197.7 766.6 201.7 772.7 203.7 778.7 205.8 784.7 207.9 787.7 209 790.7 210 793.7 211.1 795.1 211.6 796.6 212.1 798 212.7 798.7 213 799.4 213.2 800.1 213.5 800.8 213.8 801.9 214 802.4 214.5 803.6 215.7 805.3 216.5 806.3 217.9 806.8 218.7 807.1 219.5 807.2 220.5 807.3 221.2 807.2 221.8 807.4 222.5 807.7 223.4 807.9 224.3 808.1 225.2 809.8 231.5 811.2 237.9 812.3 244.4 813.4 250.8 814.1 257.2 814.5 263.6 814.7 266.8 814.8 270 814.9 273.2 814.9 274 814.9 274.7 814.9 275.5 814.9 276.3 815.2 277.1 815.3 277.8 815.7 279.5 816 281.1 816.4 282.8 821.3 306.5 822.7 330.7 820.7 354.8 819.6 367.7 817.6 380.7 814.8 393.5 807.1 421.7 822.5 357.6 814.8 393.5ZM617.6 393.5C616.1 389 614.6 384.5 613.1 379.9 612.9 379.3 612.7 378.7 612.5 378.1 612.4 377.7 612.5 377.1 612.4 376.7 612.3 376.1 612.2 375.5 612.1 374.9 611.8 373.8 611.4 372.8 610.8 371.9 609.7 370.1 608.1 368.5 606.5 367 604.7 365.2 602.4 362.7 599.6 362.7 601.6 360.7 604.3 360 606.5 358.3 607.6 357.4 608.5 356.5 609.7 355.7 610.5 355.2 611.6 354.7 612.1 353.8 612.3 353.4 612.4 352.9 612.4 352.5 612.9 352 613.3 351.5 613.7 350.9 614.4 349.8 614.7 348.6 614.9 347.3 615.1 345.1 615 342.9 615 340.7 615 338.4 615 336.1 615 333.8 615 331.4 615 329 614.4 326.6 613.1 321.5 610 316.8 606.4 313.1 604.7 311.4 603 309.9 601 308.6 598.3 306.9 595.5 305.5 592.7 304.1 589.9 302.7 586.9 301.8 583.8 301.4 581.4 301.1 579 301.1 576.6 301.1 573.9 301.1 571.2 301.1 568.5 301.1 556.2 301.1 543.8 301.1 531.5 301.1 526.9 301.1 522.3 301.1 517.7 301.1 516.9 301.1 516.1 301.1 515.2 301.1 515.1 301.1 515.2 305.3 515.2 305.6 515.2 308.8 515.2 311.9 515.2 315.1 515.2 316.2 515.2 317.3 515.2 318.4 515.2 318.9 515 319.1 515.5 319.1 516.7 319.1 528 319 528 319.2 528 327.2 528 335.2 528 343.2 528 355.8 528 368.3 528 380.9 528 384.6 528 388.3 528 392 528 392.2 528.1 393.4 527.9 393.4 525.4 393.4 522.8 393.4 520.3 393.4 518.9 393.4 517.6 393.4 516.2 393.4 515.9 393.4 515.2 393.2 515.2 393.6 515.2 395.7 515.2 397.8 515.2 400 515.2 401 515.2 414 515.2 414 524.7 414 534.3 414 543.8 414 549.3 414 554.8 414 560.2 414 561.4 414 562.5 414 563.7 414 564 414 563.8 411.1 563.8 410.7 563.8 405.1 563.8 399.6 563.8 394 563.8 393.4 563.9 393.5 563.3 393.5 562 393.5 560.7 393.5 559.3 393.5 557.8 393.5 556.3 393.5 554.8 393.5 554.6 393.5 553.5 393.7 553.5 393.4 553.5 388.4 553.5 383.4 553.5 378.4 553.5 375.6 553.5 372.9 553.5 370.1 553.5 369.4 553.5 368.8 553.5 368.1 553.5 367.7 554.2 367.9 554.5 367.9 557.4 367.9 560.2 367.9 563.1 367.9 565 367.9 566.9 367.9 568.8 367.9 570.1 367.9 571.6 367.7 572.8 368.1 573.9 368.4 574.8 369 575.7 369.7 576.8 370.6 578.3 371.8 578.9 373.1 579.2 373.8 579.2 374.5 579.2 375.3 579.2 376.6 579.6 377.7 580.2 378.9 580.7 380 581.3 381 581.6 382.2 581.7 382.6 581.7 383 581.8 383.4 581.9 384 582 384.6 582.1 385.1 583.1 390.9 584.2 396.6 585.2 402.4 585.6 404.9 586.1 407.3 586.5 409.8 586.6 410.3 586.7 410.8 586.8 411.3 586.8 411.4 587.2 411.4 587.4 411.4 597.8 411.4 608.3 411.4 618.7 411.4 619.2 411.4 619.6 411.4 620.1 411.4 620.2 411.4 620.2 410.7 620.2 410.6 620.2 408.2 620.2 405.7 620.2 403.3 620.2 398.3 620.2 393.3 620.2 388.4 620.2 388.4 620.2 388.4 620.2 388.4 619.3 390.1 618.5 391.8 617.6 393.5ZM592 339.7C592 342 589.2 342.8 587.7 344.1 587.4 344.3 587.1 344.6 586.9 344.8 586.7 344.8 586.4 344.8 586.2 344.9 585.8 345 585.4 345.2 585.1 345.4 584.4 345.9 583.9 346.6 583.2 347 582.1 347.5 580.7 347.3 579.6 347.3 577.9 347.3 576.3 347.3 574.6 347.3 573.9 347.3 573.2 347.3 572.5 347.3 569.5 347.3 566.4 347.3 563.4 347.3 563 347.3 558.8 347.4 558.8 347.2 558.8 337.9 558.8 328.5 558.8 319.2 558.8 319.1 571.7 319.2 573 319.2 577 319.2 581 319.1 584.9 320.1 586.4 320.5 587.8 321 589.2 321.6 590.1 322.1 591 323.2 591.6 324 593.1 325.7 594.1 327.8 594.5 330 594.6 330.7 594.6 331.3 594.6 332 594.3 332.6 594 333.2 593.7 333.9 593.3 334.7 592.9 335.5 592.6 336.3 592.1 337.4 592 338.5 592 339.7ZM722.6 393.5C722.6 384.2 722.6 374.9 722.6 365.6 722.6 357.1 720.9 348 714.6 341.9 707.5 335.1 696.4 333.9 687 334.7 685.1 334.9 683.2 335.3 681.4 336.1 680.4 336.5 679.5 336.9 678.6 337.6 678 338.1 677.3 338.5 676.7 338.8 673.6 340.4 670.5 341.6 668.8 344.9 668.8 335.9 668.8 326.8 668.8 317.8 668.8 311.9 668.8 306 668.8 300.1 668.8 298.4 668.8 296.6 668.8 294.9 668.8 294.4 669.1 293.7 668.5 293.7 657.9 293.7 647.3 293.7 636.7 293.7 635.5 293.7 634.2 293.7 633 293.7 633 293.7 633 297.8 633 298.1 633 303.4 633 308.7 633 314 633 314.3 633.8 314.2 634 314.2 635.4 314.2 636.7 314.2 638.1 314.2 640.6 314.2 643.2 314.2 645.7 314.2 645.9 314.2 645.8 319.4 645.8 319.8 645.8 331.2 645.8 342.6 645.8 353.9 645.8 364.9 645.8 375.8 645.8 386.8 645.8 388 645.8 389.2 645.8 390.3 645.8 391.2 645.7 391 644.6 391 641.6 391 638.7 391 635.7 391 634.8 391 633.9 391 633 391 632.9 391 632.9 391.9 632.9 392 632.9 397.7 632.9 403.4 632.9 409 632.9 409.8 632.9 410.5 632.9 411.3 632.9 411.5 633 411.5 633.2 411.5 634.5 411.5 635.9 411.5 637.2 411.5 649.1 411.5 661 411.5 672.9 411.5 673.4 411.5 681.5 411.5 681.5 411.5 681.5 406.5 681.5 401.5 681.5 396.5 681.5 394.7 681.5 392.9 681.5 391.1 681.5 391.1 675.6 391.1 675.2 391.1 674.8 391.1 668.7 391.1 668.7 391.1 668.7 389.8 668.7 388.5 668.7 387.3 668.7 381.2 668.7 375 668.7 368.9 668.7 366.5 668.7 364.2 668.7 361.8 668.7 361.3 668.7 360.9 668.7 360.4 668.7 360 670.3 358.8 670.6 358.5 671.7 357.5 672.8 356.5 674.2 355.8 674.7 355.5 675.3 355.3 675.8 355.3 676.5 355.2 676.8 354.8 677.4 354.3 678.5 353.5 679.7 353 681 352.8 683.6 352.4 685.8 352.7 687.9 354.2 689.1 355.1 690.1 356.1 691.2 357.2 692 358 692.7 358.8 693.3 359.8 694.2 361.6 694.3 363.7 694.3 365.7 694.4 369.3 694.3 372.9 694.3 376.6 694.3 387.8 694.3 399 694.3 410.3 694.3 410.9 694 411.6 694.7 411.6 696.4 411.6 698.1 411.6 699.8 411.6 706 411.6 712.3 411.6 718.5 411.6 722.4 411.6 726.3 411.6 730.2 411.6 730.2 411.6 730.2 398.5 730.2 397.5 730.2 395.4 730.2 393.3 730.2 391.2 727.8 391.8 725.2 392.6 722.6 393.5ZM730.3 270.6C727.9 270.6 725.4 270.6 723 270.6 722 270.6 721.1 270.6 720.1 270.6 720 270.6 719.6 271.3 719.6 271.4 716.5 276 713.4 280.6 710.4 285.3 708.9 287.5 707.4 289.7 706 292 705.6 292.5 705.3 293.1 704.9 293.6 704.6 294.1 704.8 294.9 704.8 295.4 704.8 295.6 704.8 298.8 704.8 298.8 705.4 298.8 706 298.8 706.5 298.8 709.5 298.8 712.4 298.8 715.4 298.8 717.8 298.8 720.1 298.8 722.5 298.8 723 298.8 722.7 299.6 722.7 299.9 722.7 301.4 722.7 302.9 722.7 304.4 722.7 305.8 722.7 307.1 722.7 308.5 722.7 309.3 723 309.1 723.8 309.1 725.3 309.1 726.9 309.1 728.4 309.1 728.7 309.1 730.3 309.3 730.3 308.9 730.3 306.2 730.3 303.4 730.3 300.7 730.3 300.4 730.1 298.8 730.5 298.8 731.9 298.8 733.3 298.8 734.6 298.8 734.7 298.8 735.4 298.8 735.4 298.8 735.4 298.2 735.4 297.7 735.4 297.1 735.4 296.9 735.4 293.7 735.4 293.7 734.1 293.7 732.9 293.7 731.6 293.7 731.1 293.7 730.3 294 730.3 293.4 730.3 285.7 730.3 278.1 730.3 270.6ZM722.6 285.9C722.6 287.2 722.6 288.5 722.6 289.7 722.6 290.6 722.6 291.4 722.6 292.3 722.6 292.5 722.7 293.4 722.6 293.6 722.5 293.7 721.6 293.6 721.5 293.6 720.6 293.6 719.7 293.6 718.8 293.6 717.5 293.6 716.2 293.6 715 293.6 716.3 291.6 717.7 289.6 719 287.6 719.6 286.7 720.2 285.9 720.8 285.1 722.4 283.1 722.6 280.7 722.6 278.2 722.6 280.8 722.6 283.4 722.6 285.9ZM763.6 288.5C760.9 285.8 756.2 285.9 752.6 285.9 752 285.9 751.4 285.9 750.8 285.9 750.8 285.9 750.8 284.8 750.8 284.7 750.8 283.4 750.8 282.1 750.8 280.8 750.8 280.7 763.9 280.8 765.2 280.8 765.7 280.8 766.2 281 766.2 280.5 766.2 279.1 766.2 277.7 766.2 276.4 766.2 275.3 766.2 274.2 766.2 273.2 766.2 273.2 764.9 273.2 764.9 273.2 759.2 273.2 753.5 273.2 747.8 273.2 747.2 273.2 746.5 273.2 745.9 273.2 745.7 273.2 745.7 273.6 745.7 273.8 745.4 276 745.1 278.2 744.9 280.4 744.3 284.8 743.8 289.3 743.2 293.7 747 293.7 751.5 293.1 755.1 294.8 757.9 296.2 759 299.4 758.5 302.4 758 305.8 754.4 306.5 751.5 306.5 749.6 306.5 743.2 307 743.2 303.9 742.3 306.5 741.5 309 740.6 311.6 742.3 311.6 744 312.6 745.6 313.2 748 314.1 750.5 314.3 753 314.1 756.9 313.8 761 312.5 763.6 309.4 766.3 306.1 766.2 301.9 766.2 297.8 766.2 295.6 766.2 293.3 765.7 291.1 765.5 290.1 765 288.6 763.7 288.5 763.7 288.5 763.6 288.5 763.6 288.5 761 285.9 766.2 288.5 763.6 288.5Z",
88 "width": 1000
89 },
90 "search": [
91 "rhodecode"
92 ]
93 },
94 {
95 "uid": "e5ad8728e6d6290aff4b6ffcfcaa9167",
96 "css": "up",
97 "code": 59442,
98 "src": "custom_icons",
99 "selected": true,
100 "svg": {
101 "path": "M686.5 595.8L513.6 379.1C506.3 369.9 492.4 369.9 485.1 379.1L312.2 595.8C302.7 607.8 311.2 625.4 326.5 625.4H672.2C687.5 625.4 696 607.8 686.5 595.8Z",
102 "width": 1000
103 },
104 "search": [
105 "up"
106 ]
107 },
108 {
109 "uid": "6e459e39444c93a2c017f258186765d6",
110 "css": "unlock",
111 "code": 59399,
112 "src": "custom_icons",
113 "selected": true,
114 "svg": {
115 "path": "M780.8 434.6H396.2V342.3C396.2 284.6 438.5 238.5 492.3 226.9 492.3 226.9 492.3 226.9 496.2 226.9 503.8 226.9 507.7 226.9 515.4 226.9 515.4 226.9 519.2 226.9 519.2 226.9 519.2 226.9 519.2 226.9 523.1 226.9 530.8 226.9 538.5 226.9 546.2 230.8 546.2 230.8 546.2 230.8 546.2 230.8 553.8 230.8 557.7 234.6 565.4 238.5 565.4 238.5 569.2 238.5 569.2 242.3 573.1 246.2 580.8 246.2 584.6 250 584.6 250 584.6 250 584.6 250 588.5 253.8 596.2 257.7 600 261.5 600 261.5 603.8 265.4 603.8 265.4 607.7 269.2 611.5 273.1 615.4 276.9 615.4 276.9 615.4 276.9 619.2 280.8 623.1 284.6 626.9 292.3 630.8 300 630.8 300 630.8 303.8 630.8 303.8 634.6 307.7 634.6 315.4 634.6 319.2 634.6 319.2 634.6 323.1 634.6 323.1 634.6 323.1 634.6 323.1 634.6 326.9 638.5 338.5 646.2 346.2 657.7 346.2H715.4C730.8 346.2 742.3 334.6 738.5 319.2 738.5 319.2 738.5 319.2 738.5 319.2 738.5 319.2 738.5 315.4 738.5 315.4 738.5 307.7 734.6 303.8 734.6 296.2 734.6 292.3 734.6 292.3 730.8 288.5 730.8 273.1 730.8 269.2 726.9 261.5 726.9 261.5 726.9 257.7 723.1 257.7 719.2 250 715.4 242.3 711.5 234.6 711.5 234.6 707.7 230.8 707.7 230.8 703.8 223.1 700 219.2 696.2 215.4 696.2 211.5 692.3 211.5 692.3 207.7 688.5 203.8 684.6 196.2 680.8 192.3 680.8 192.3 676.9 188.5 676.9 188.5 669.2 180.8 665.4 176.9 657.7 169.2 657.7 169.2 653.8 169.2 653.8 165.4 650 161.5 642.3 157.7 634.6 153.8 630.8 153.8 630.8 150 626.9 150 623.1 146.2 615.4 142.3 611.5 142.3 607.7 142.3 607.7 138.5 603.8 138.5 596.2 134.6 588.5 130.8 580.8 130.8 580.8 130.8 580.8 130.8 580.8 130.8 573.1 126.9 565.4 126.9 553.8 123.1 550 123.1 550 123.1 546.2 123.1 538.5 123.1 534.6 123.1 526.9 119.2 523.1 119.2 519.2 119.2 519.2 119.2 511.5 119.2 503.8 119.2 496.2 119.2 496.2 119.2 492.3 119.2 492.3 119.2 484.6 119.2 476.9 123.1 465.4 123.1 461.5 123.1 453.8 126.9 450 126.9 450 126.9 446.2 126.9 446.2 126.9 353.8 153.8 288.5 242.3 288.5 342.3V434.6H246.2C230.8 434.6 223.1 446.2 223.1 457.7V857.7C223.1 873.1 234.6 880.8 246.2 880.8H780.8C796.2 880.8 803.8 869.2 803.8 857.7V457.7C807.7 446.2 796.2 434.6 780.8 434.6Z",
116 "width": 1000
117 },
118 "search": [
119 "unlock"
120 ]
121 },
122 {
123 "uid": "b077586592b9b69166b981325446c836",
124 "css": "delete",
125 "code": 59392,
126 "src": "custom_icons",
127 "selected": true,
128 "svg": {
129 "path": "M515.4 92.3C303.8 92.3 130.8 265.4 130.8 476.9 130.8 688.5 303.8 861.5 515.4 861.5S900 688.5 900 476.9C900 265.4 726.9 92.3 515.4 92.3ZM742.3 507.7C742.3 523.1 730.8 534.6 711.5 534.6H315.4C300 534.6 284.6 523.1 284.6 507.7V446.2C284.6 430.8 296.2 419.2 315.4 419.2H711.5C726.9 419.2 742.3 430.8 742.3 446.2V507.7Z",
130 "width": 1000
131 },
132 "search": [
133 "delete"
134 ]
135 },
136 {
137 "uid": "dca63ad885c0d6f1780a8d1d55bc2380",
138 "css": "ok",
139 "code": 59393,
140 "src": "custom_icons",
141 "selected": true,
142 "svg": {
143 "path": "M515.4 115.4C303.8 115.4 130.8 288.5 130.8 500 130.8 711.5 303.8 884.6 515.4 884.6S900 711.5 900 500C900 288.5 726.9 115.4 515.4 115.4ZM753.8 411.5L450 715.4C438.5 726.9 423.1 726.9 411.5 715.4L273.1 576.9C261.5 565.4 261.5 550 273.1 538.5L315.4 496.2C326.9 484.6 342.3 484.6 353.8 496.2L411.5 553.8C423.1 565.4 438.5 565.4 450 553.8L669.2 334.6C680.8 323.1 696.2 323.1 707.7 334.6L750 376.9C765.4 384.6 765.4 400 753.8 411.5Z",
144 "width": 1000
145 },
146 "search": [
147 "ok"
148 ]
149 },
150 {
151 "uid": "c158b3a004c055c6ad1471cd98932268",
152 "css": "down",
153 "code": 59403,
154 "src": "custom_icons",
155 "selected": true,
156 "svg": {
157 "path": "M703.8 396.2L530.8 615.4C523.1 623.1 507.7 623.1 503.8 615.4L330.8 396.2C323.1 384.6 330.8 365.4 346.2 365.4H692.3C703.8 365.4 711.5 384.6 703.8 396.2Z",
158 "width": 1000
159 },
160 "search": [
161 "arrow_down"
162 ]
163 },
164 {
165 "uid": "02f59f392ad28056845cfc04cb121f13",
166 "css": "comment",
167 "code": 59394,
168 "src": "custom_icons",
169 "selected": true,
170 "svg": {
171 "path": "M130.8 784.6V280.8C130.8 207.7 188.5 150 261.5 150H769.2C842.3 150 900 207.7 900 280.8V569.2C900 642.3 842.3 700 769.2 700H273.1C269.2 700 261.5 703.8 257.7 707.7L165.4 800C153.8 815.4 130.8 803.8 130.8 784.6ZM261.5 211.5C223.1 211.5 188.5 242.3 188.5 284.6V696.2L234.6 650C238.5 646.2 242.3 642.3 250 642.3H769.2C807.7 642.3 842.3 611.5 842.3 569.2V280.8C842.3 242.3 811.5 207.7 769.2 207.7H261.5Z",
172 "width": 1000
173 },
174 "search": [
175 "comment"
176 ]
177 },
178 {
179 "uid": "9a44b838872ca62b8aba7bbbbf67cc59",
180 "css": "feed",
181 "code": 59400,
182 "src": "custom_icons",
183 "selected": true,
184 "svg": {
185 "path": "M842.3 111.5H188.5C153.8 111.5 130.8 138.5 130.8 169.2V826.9C130.8 857.7 157.7 884.6 188.5 884.6H846.2C876.9 884.6 903.8 857.7 903.8 826.9V169.2C900 138.5 873.1 111.5 842.3 111.5ZM307.7 776.9C269.2 776.9 234.6 746.2 234.6 703.8S265.4 630.8 307.7 630.8C346.2 630.8 380.8 661.5 380.8 703.8S346.2 776.9 307.7 776.9ZM553.8 788.5C519.2 788.5 496.2 761.5 496.2 730.8 496.2 619.2 407.7 530.8 296.2 530.8 265.4 530.8 230.8 503.8 230.8 473.1 230.8 438.5 253.8 411.5 284.6 411.5L296.2 411.5C473.1 411.5 615.4 553.8 615.4 730.8 611.5 761.5 584.6 788.5 553.8 788.5ZM750 788.5C715.4 788.5 692.3 761.5 692.3 730.8 692.3 511.5 511.5 330.8 292.3 330.8 261.5 330.8 226.9 303.8 226.9 269.2 226.9 234.6 250 207.7 280.8 207.7L292.3 207.7C576.9 207.7 811.5 438.5 811.5 726.9 811.5 761.5 784.6 788.5 750 788.5Z",
186 "width": 1000
187 },
188 "search": [
189 "feed"
190 ]
191 },
192 {
193 "uid": "e0118d6f20b76d77317977ae8dc849d7",
194 "css": "left",
195 "code": 59401,
196 "src": "custom_icons",
197 "selected": true,
198 "svg": {
199 "path": "M692.3 76.9L761.5 146.2C773.1 157.7 773.1 173.1 761.5 184.6L473.1 473.1C461.5 484.6 461.5 500 473.1 511.5L769.2 807.7C780.8 819.2 780.8 834.6 769.2 846.2L700 915.4C688.5 926.9 673.1 926.9 661.5 915.4L257.7 511.5C246.2 500 246.2 484.6 257.7 473.1L653.8 76.9C665.4 65.4 680.8 65.4 692.3 76.9Z",
200 "width": 1000
201 },
202 "search": [
203 "left"
204 ]
205 },
206 {
207 "uid": "3cea97f90c8f2b0a90833855434f58de",
208 "css": "right",
209 "code": 59402,
210 "src": "custom_icons",
211 "selected": true,
212 "svg": {
213 "path": "M338.5 915.4L265.4 846.2C253.8 834.6 253.8 819.2 265.4 807.7L553.8 519.2C565.4 507.7 565.4 492.3 553.8 480.8L257.7 184.6C246.2 173.1 246.2 157.7 257.7 146.2L326.9 76.9C338.5 65.4 353.8 65.4 365.4 76.9L769.2 480.8C780.8 492.3 780.8 507.7 769.2 519.2L376.9 915.4C365.4 926.9 346.2 926.9 338.5 915.4Z",
214 "width": 1000
215 },
216 "search": [
217 "right"
218 ]
219 },
220 {
221 "uid": "820a44cb2e7fc1d0e28b1d2a8cd44cb9",
222 "css": "git",
223 "code": 59434,
224 "src": "custom_icons",
225 "selected": true,
226 "svg": {
227 "path": "M928.8 6.3H71.3C35 6.3 6.3 36.3 6.3 71.3V927.5C6.3 963.8 36.3 992.5 71.3 992.5H927.5C963.8 992.5 992.5 962.5 992.5 927.5V71.3C993.8 36.3 963.7 6.3 928.8 6.3ZM200 555C203.8 566.3 208.8 575 213.8 582.5 220 590 227.5 596.3 236.3 600 245 603.8 255 606.3 265 606.3 273.8 606.3 281.3 605 288.8 603.8 296.3 602.5 302.5 600 308.8 597.5L315 546.3H287.5C283.8 546.3 280 545 277.5 542.5 276.3 541.3 275 537.5 275 535L280 496.2H385L368.7 627.5C361.2 633.8 352.5 638.7 343.7 642.5 335 646.3 326.3 650 316.2 652.5 306.2 655 297.5 657.5 286.3 658.8 276.3 660 265 661.3 252.5 661.3 232.5 661.3 215 657.5 198.7 650 182.5 642.5 168.7 632.5 157.5 620 146.2 607.5 137.5 592.5 131.2 575 125 557.5 121.2 538.8 121.2 518.8 121.2 501.3 123.7 485 127.5 468.8 131.2 452.5 137.5 438.8 145 425 152.5 411.3 161.2 400 171.2 388.8 181.2 377.5 192.5 368.8 205 361.3 217.5 353.8 231.3 347.5 246.3 343.8 261.3 340 276.3 337.5 292.5 337.5 306.3 337.5 317.5 338.8 328.7 341.3 340 343.8 350 347.5 357.5 351.3 366.2 355 373.8 360 380 365 386.3 370 392.5 376.3 397.5 381.3L377.5 412.5C373.8 417.5 368.8 420 363.8 421.3 358.8 422.5 353.7 421.3 347.5 417.5 342.5 413.8 337.5 411.3 333.7 408.8 328.7 406.3 325 403.8 320 402.5 315 401.3 310 400 305 398.8 300 397.5 293.7 397.5 287.5 397.5 273.7 397.5 261.2 400 250 406.3 238.7 412.5 228.7 420 221.2 431.3 212.5 441.2 206.2 455 202.5 468.8 197.5 483.8 196.2 500 196.2 517.5 195 531.3 197.5 543.8 200 555ZM536.3 657.5H465L503.7 342.5H575L536.3 657.5ZM878.8 398.8H798.8L766.3 657.5H696.3L727.5 398.7H647.5L655 342.5H886.3L878.8 398.8Z",
228 "width": 1000
229 },
230 "search": [
231 "git"
232 ]
233 },
234 {
235 "uid": "ea152b092f5ad7d610de2c388553e188",
236 "css": "hg",
237 "code": 59437,
238 "src": "custom_icons",
239 "selected": true,
240 "svg": {
241 "path": "M926.6 9.2H73.9C37.9 9.2 8.7 38.5 8.7 74.4V927.1C8.7 963.1 38 992.3 73.9 992.3H926.6C962.6 992.3 991.8 963 991.8 927.1V74.4C991.8 38.4 962.6 9.2 926.6 9.2ZM444 657.4H373.5L389.8 524.1H276.7L260.4 657.4H189.9L228.6 344.2H299.1L282.8 476.4H395.9L412.2 344.2H482.7L444 657.4ZM621 555.8C624.3 566.8 629.1 576 635.3 583.5 641.5 591 648.8 596.8 657.5 600.8 666.1 604.8 675.6 606.8 686.1 606.8 694.7 606.8 702.4 606 709.3 604.5 716.2 603 722.8 600.8 729.1 598.1L735.1 546.9H708.4C704.1 546.9 700.8 545.8 698.6 543.6 696.4 541.4 695.5 538.5 695.9 534.9L700.6 496.2H805.1L788.8 627.1C780.8 633 772.5 638.1 763.9 642.3 755.3 646.6 746.3 650 736.9 652.7 727.5 655.5 717.6 657.5 707.2 658.7 696.8 660 685.7 660.6 674 660.6 654.6 660.6 637 657 621 650 605 642.9 591.3 633.1 579.9 620.7 568.5 608.2 559.7 593.5 553.5 576.4 547.2 559.3 544.1 540.9 544.1 520.9 544.1 503.6 546.1 487.1 550 471.3 554 455.6 559.6 441.1 566.9 427.8 574.2 414.5 583 402.4 593.2 391.7 603.4 381 614.9 371.8 627.4 364.2 639.9 356.6 653.5 350.7 667.9 346.6 682.4 342.6 697.6 340.5 713.5 340.5 726.8 340.5 738.9 341.7 749.7 344.2 760.5 346.6 770.2 349.9 778.8 353.9 787.4 358 795.1 362.8 801.8 368.1 808.6 373.5 814.5 379 819.7 384.8L797 413.2C793.3 418.2 788.8 421.3 783.7 422.3 778.6 423.4 773.2 422.2 767.8 418.8 762.8 415.4 758.1 412.4 753.6 409.9 749.2 407.4 744.7 405.3 740.1 403.7 735.5 402 730.7 400.8 725.6 400 720.5 399.2 714.8 398.8 708.5 398.8 694.9 398.8 682.4 401.7 671.1 407.5 659.8 413.3 650 421.5 641.9 432 633.7 442.5 627.4 455.2 622.9 469.9 618.4 484.7 616.1 501 616.1 518.7 615.9 532.5 617.6 544.8 621 555.8Z",
242 "width": 1000
243 },
244 "search": [
245 "hg"
246 ]
247 },
248 {
249 "uid": "4a842c0afb4c35dacd21da71f9fed3f1",
250 "css": "comment-add",
251 "code": 59439,
252 "src": "custom_icons",
253 "selected": true,
254 "svg": {
255 "path": "M952.4 591.9V274.9C952.4 268.4 952.3 261.9 951.8 255.4 950.7 242.9 948.2 230.6 944.1 218.8 936.5 196.6 923.8 176.2 907.3 159.6 890.8 143.1 870.6 130.4 848.5 122.7 836.6 118.6 824.2 115.9 811.6 114.8 805.3 114.2 798.9 114.2 792.6 114.2H216.9C204 114.2 191.3 114.1 178.5 116 166.3 117.9 154.4 121.2 143 125.9 121.4 134.8 101.9 148.7 86.4 166.2 70.8 183.8 59.3 205 53.1 227.7 49.7 240.1 47.9 252.8 47.6 265.6 47.3 278.7 47.6 291.8 47.6 304.9V861.8C47.6 870.7 52.5 878.6 60.5 882.5 67.3 885.9 75.6 886.2 82.4 882.7 84.8 881.5 86.9 879.7 88.8 877.8 91.1 875.5 93.4 873.2 95.6 871 100.3 866.3 105 861.6 109.7 856.9L137.9 828.6C147.3 819.2 156.6 809.9 166 800.5 175.2 791.3 184.6 782.1 193.7 772.7 197.7 768.5 201.9 764.4 207.6 762.7 210.4 761.9 213.2 761.8 216 761.8H782.7C795.5 761.8 808.3 762 821 760.1 844.8 756.5 867.7 747.3 887.3 733.3 906.2 719.9 922.1 702.1 933.2 681.8 945.1 660.2 951.5 636 952.2 611.4 952.5 604.9 952.4 598.4 952.4 591.9ZM883.4 285.1V602.5C883.4 608.8 883.4 615.1 882.5 621.4 881.7 627.5 880.2 633.6 878.1 639.4 874.4 649.4 868.8 658.7 861.7 666.7 846.6 683.6 825.1 693.8 802.5 695.1 796.3 695.4 790 695.2 783.8 695.2H207.8C201.2 695.2 194.7 695.2 188.1 695.2 185 695.2 181.8 695.2 178.8 696.1 176.2 696.9 173.9 698.2 171.8 699.9 169.6 701.7 167.6 703.7 165.6 705.7 163.3 708 161 710.3 158.7 712.6 154 717.3 149.4 721.9 144.7 726.6 135.3 736 126 745.3 116.6 754.7V270C116.6 257.8 118.8 245.7 123.7 234.6 128 224.9 134 215.9 141.5 208.4 157.5 192.4 179.6 183.3 202.2 183.3H791.5C797.6 183.3 803.7 183.3 809.7 184.2 832 187.4 852.4 199.4 866 217.4 872.8 226.4 877.7 236.7 880.5 247.6 882 253.5 882.9 259.6 883.1 265.8 883.6 272.2 883.4 278.7 883.4 285.1ZM668.8 402H538.2C534.4 402 526.7 394.3 526.7 390.5V263.7C526.7 256 519 248.3 515.2 248.3H465.3C457.6 248.3 449.9 256 449.9 259.8V390.4C449.9 394.2 442.2 401.9 438.4 401.9H311.7C304 401.9 296.3 409.6 296.3 413.4V463.3C296.3 471 304 478.7 307.8 478.7H434.5C442.2 478.7 449.9 486.4 449.9 490.2V617C449.9 624.7 457.6 632.4 461.4 632.4H511.3C519 632.4 526.7 624.7 526.7 620.9V494.1C526.7 486.4 534.4 478.7 538.2 478.7H665C672.7 478.7 680.4 471 680.4 467.2V417.3C680.3 409.6 672.6 402 668.8 402Z",
256 "width": 1000
257 },
258 "search": [
259 "comment-add"
260 ]
261 },
262 {
263 "uid": "2427f6b8d4379b9a0b41cf31780807cf",
264 "css": "comment-toggle",
265 "code": 59440,
266 "src": "custom_icons",
267 "selected": true,
268 "svg": {
269 "path": "M797.6 114.2H202.4C116.6 114.2 47.6 183.3 47.6 269V861.9C47.6 881.4 69.5 891.1 84.1 881.8 86.4 880.7 88.6 879.1 90.6 877.1L199.8 768C202.1 765.7 204.7 764 207.7 762.8 209.7 762.2 211.9 761.9 214.3 761.9H797.6C883.4 761.9 952.4 692.8 952.4 607.1V269C952.4 183.2 883.3 114.2 797.6 114.2ZM118.3 752.6V269.5C118.3 222.5 156.4 184.3 203.5 184.3H680.1C593.7 267.9 175.5 695.4 171.4 699.5L118.3 752.6Z",
270 "width": 1000
271 },
272 "search": [
273 "comment-toggle"
274 ]
275 },
276 {
277 "uid": "6533bdc16ab201eb3f3b27ce989cab33",
278 "css": "folder-open-empty",
279 "code": 61717,
280 "src": "fontawesome"
281 },
282 {
283 "uid": "d64b34fac1d9923b7d29d1550b628ecd",
284 "css": "lock",
285 "code": 59398,
286 "src": "custom_icons",
287 "selected": true,
288 "svg": {
289 "path": "M812.5 424.1H758.9V317C758.9 308 758.9 303.6 758.9 299.1 758.9 294.6 758.9 290.2 758.9 285.7 758.9 281.3 758.9 281.3 758.9 276.8 758.9 267.9 758.9 263.4 754.5 254.5 754.5 250 754.5 250 750 245.5 750 236.6 745.5 232.1 741.1 223.2 741.1 223.2 741.1 218.8 736.6 218.8 732.1 209.8 727.7 200.9 723.2 192 723.2 192 718.8 187.5 718.8 187.5 723.2 178.6 718.8 169.6 714.3 165.2 714.3 160.7 709.8 160.7 709.8 156.3 705.4 151.8 700.9 142.9 696.4 138.4 696.4 138.4 692 133.9 692 133.9 683 125 678.6 120.5 669.6 111.6 669.6 111.6 665.2 111.6 665.2 107.1 660.7 102.7 651.8 98.2 642.9 93.8 638.4 93.8 638.4 89.3 633.9 89.3 629.5 84.8 620.5 80.4 616.1 80.4 611.6 80.4 611.6 75.9 607.1 75.9 598.2 71.4 589.3 67 580.4 67 580.4 67 580.4 67 580.4 67 571.4 62.5 562.5 62.5 549.1 58 544.6 58 544.6 58 540.2 58 535.7 58 535.7 58 531.3 58 531.3 58 526.8 58 526.8 58 526.8 58 522.3 58 522.3 58 522.3 58 522.3 58 522.3 58 522.3 58 522.3 58 522.3 58 517.9 58 513.4 58 513.4 58 513.4 58 508.9 58 508.9 58 504.5 58 504.5 58 500 58 500 58 500 58 500 58 495.5 58 491.1 58 491.1 58 491.1 58 491.1 58 491.1 58 491.1 58 491.1 58 491.1 58 491.1 58 486.6 58 486.6 58 486.6 58 482.1 58 482.1 58 477.7 58 477.7 58 473.2 58 468.8 58 468.8 58 464.3 58 455.4 58 442 62.5 433 67 433 67 433 67 433 67 410.7 67 397.3 71.4 388.4 75.9 383.9 75.9 383.9 80.4 379.5 80.4 375 84.8 370.5 84.8 361.6 89.3 361.6 93.8 357.1 93.8 357.1 93.8 348.2 98.2 339.3 102.7 334.8 111.6 334.8 111.6 330.4 111.6 330.4 116.1 321.4 120.5 317 125 308 133.9 308 133.9 303.6 138.4 303.6 138.4 299.1 142.9 294.6 151.8 290.2 156.3 290.2 160.7 285.7 160.7 285.7 165.2 276.8 169.6 272.3 178.6 272.3 183 267.9 183 267.9 187.5 267.9 187.5 263.4 196.4 258.9 205.4 254.5 214.3 254.5 214.3 254.5 218.8 250 218.8 250 232.1 245.5 236.6 245.5 245.5 245.5 250 245.5 250 241.1 254.5 241.1 263.4 236.6 267.9 236.6 276.8 236.6 281.3 236.6 281.3 236.6 285.7 236.6 290.2 236.6 294.6 236.6 299.1 236.6 303.6 236.6 312.5 236.6 317V424.1H187.5C169.6 424.1 160.7 437.5 160.7 450.9V915.2C160.7 933 174.1 942 187.5 942H808C825.9 942 834.8 928.6 834.8 915.2V450.9C839.3 433 825.9 424.1 812.5 424.1ZM361.6 317C361.6 250 410.7 196.4 473.2 183 473.2 183 473.2 183 477.7 183 486.6 183 491.1 183 500 183 500 183 504.5 183 504.5 183 504.5 183 504.5 183 504.5 183 513.4 183 517.9 183 526.8 183 526.8 183 526.8 183 531.3 183 593.8 196.4 642.9 250 642.9 317V424.1H361.6V317Z",
290 "width": 1000
291 },
292 "search": [
293 "lock"
294 ]
295 },
296 {
297 "uid": "d95fde5e3bfeb3302efc47c90538a1c5",
298 "css": "more",
299 "code": 59410,
300 "src": "custom_icons",
301 "selected": true,
302 "svg": {
303 "path": "M546.2 415.4H446.2C430.8 415.4 419.2 426.9 419.2 442.3V542.3C419.2 557.7 430.8 569.2 446.2 569.2H546.2C561.5 569.2 573.1 557.7 573.1 542.3V442.3C573.1 426.9 561.5 415.4 546.2 415.4ZM546.2 107.7H446.2C430.8 107.7 419.2 119.2 419.2 134.6V234.6C419.2 250 430.8 261.5 446.2 261.5H546.2C561.5 261.5 573.1 250 573.1 234.6V134.6C573.1 119.2 561.5 107.7 546.2 107.7ZM546.2 723.1H446.2C430.8 723.1 419.2 734.6 419.2 750V850C419.2 865.4 430.8 876.9 446.2 876.9H546.2C561.5 876.9 573.1 865.4 573.1 850V750C573.1 734.6 561.5 723.1 546.2 723.1Z",
304 "width": 1000
305 },
306 "search": [
307 "more"
308 ]
309 },
310 {
311 "uid": "34e7772638ae3ca1bfb0a4eca2c39221",
312 "css": "merge",
313 "code": 59443,
314 "src": "custom_icons",
315 "selected": true,
316 "svg": {
317 "path": "M199.8 740.5C199.8 812.2 258.1 870.5 329.8 870.5S459.8 812.2 459.8 740.5C459.8 694.6 435.8 654.5 399.8 631.3 418.4 491.7 533.4 451.9 602.4 440.6V742.4C563.7 765 537.4 806.4 537.4 854.4 537.4 926.1 595.7 984.4 667.4 984.4S797.4 926.1 797.4 854.4C797.4 806.5 771.1 765 732.4 742.4V254.9C771.1 232.3 797.4 190.9 797.4 142.9 797.4 71.2 739.1 12.9 667.4 12.9S537.4 71.2 537.4 142.9C537.4 190.8 563.7 232.3 602.4 254.9V309.9C542.2 317.8 440.4 342.3 364.2 417.8 309.5 472.1 277.9 542.1 269.6 625.9 228.4 647.7 199.8 690.6 199.8 740.5ZM667.6 897.8C643.7 897.8 624.3 878.3 624.3 854.5S643.8 811.2 667.6 811.2C691.5 811.2 710.9 830.7 710.9 854.5S691.5 897.8 667.6 897.8ZM667.6 99.6C691.5 99.6 710.9 119 710.9 142.9S691.4 186.2 667.6 186.2C643.7 186.2 624.3 166.8 624.3 142.9S643.7 99.6 667.6 99.6ZM329.9 783.9C306 783.9 286.6 764.4 286.6 740.6S306.1 697.3 329.9 697.3C353.8 697.3 373.2 716.7 373.2 740.6S353.8 783.9 329.9 783.9Z",
318 "width": 1000
319 },
320 "search": [
321 "merge"
322 ]
323 },
324 {
325 "uid": "c95735c17a10af81448c7fed98a04546",
326 "css": "folder-open",
327 "code": 59405,
328 "src": "fontawesome"
329 },
330 {
331 "uid": "865ac833a8efcfc24a6f573705ce56b1",
332 "css": "svn",
333 "code": 59438,
334 "src": "custom_icons",
335 "selected": true,
336 "svg": {
337 "path": "M933.4 9.2H80.7C44.7 9.2 15.5 38.5 15.5 74.4V927.1C15.5 963.1 44.8 992.3 80.7 992.3H933.4C969.4 992.3 998.6 963 998.6 927.1V74.4C998.7 38.4 969.4 9.2 933.4 9.2ZM167.9 447.1C171.1 451 175.4 454.4 180.8 457.3 186.2 460.2 192.2 463 199 465.4 205.7 467.8 212.7 470.5 219.8 473.3 226.9 476.2 233.9 479.5 240.7 483.2 247.5 486.9 253.6 491.6 259 497.2 264.4 502.8 268.7 509.6 271.9 517.4 275.1 525.3 276.8 534.8 276.8 545.8 276.8 561.6 274.1 576.4 268.6 590.3 263.1 604.3 255.3 616.4 245.1 626.8 234.9 637.2 222.5 645.4 208 651.5 193.4 657.6 177 660.7 158.8 660.7 149.7 660.7 140.7 659.7 131.5 657.7S113.6 652.8 105.2 649.2C96.8 645.5 89 641.2 81.8 636.2 74.6 631.2 68.5 625.6 63.5 619.5L88.5 586.7C90.5 584.3 93 582.3 95.9 580.7 98.8 579.1 101.8 578.3 104.8 578.3 108.8 578.3 112.7 579.7 116.5 582.5 120.3 585.3 124.5 588.4 129.1 591.8 133.7 595.2 139 598.2 145.1 601.1 151.2 603.9 158.7 605.3 167.6 605.3 180.7 605.3 190.7 601.7 197.8 594.7 204.9 587.6 208.4 577.1 208.4 563.2 208.4 556.8 206.8 551.4 203.5 547.3 200.3 543.1 196 539.7 190.8 536.8 185.6 533.9 179.6 531.4 172.8 529.1 166 526.9 159.2 524.5 152.1 521.9 145.1 519.3 138.2 516.2 131.4 512.8 124.6 509.3 118.6 504.7 113.4 499 108.2 493.3 103.9 486.4 100.7 478.2 97.5 469.9 95.9 459.8 95.9 447.7 95.9 433.8 98.5 420.4 103.7 407.6 108.9 394.8 116.4 383.4 126.2 373.5 136 363.6 147.8 355.7 161.7 349.8 175.6 343.9 191.3 341 208.6 341 217.5 341 226.1 341.9 234.5 343.8S250.8 348.2 258.1 351.6C265.4 354.9 272.1 358.8 278.1 363.3 284.1 367.8 289.2 372.8 293.4 378.1L272.3 407C269.7 410.3 267.2 412.8 264.8 414.4 262.4 416 259.4 416.8 256 416.8 252.7 416.8 249.4 415.8 246.1 413.6 242.8 411.4 239.1 409.1 235 406.5 230.9 403.9 226.2 401.6 220.9 399.4 215.6 397.2 209.3 396.2 202.2 396.2 195.6 396.2 189.8 397.1 184.9 399 179.9 400.9 175.8 403.4 172.5 406.8 169.2 410.1 166.7 414 165.1 418.4 163.5 422.9 162.6 427.8 162.6 433 163.1 438.4 164.7 443.2 167.9 447.1ZM480 657.4H416.3L339.2 343.7H395.6C401.6 343.7 406.4 345.1 410 348 413.6 350.8 415.8 354.5 416.7 359L449.4 531.8C451.3 538.7 453 546.3 454.6 554.8 456.2 563.2 457.5 571.9 458.7 581 461.7 572 464.9 563.2 468.4 554.8 471.8 546.4 475.4 538.8 479.2 531.8L552.3 359C553.2 357.1 554.4 355.2 556.1 353.4 557.7 351.5 559.6 349.8 561.8 348.4 564 347 566.4 345.8 569 345 571.6 344.2 574.4 343.7 577.3 343.7H634.1L480 657.4ZM902.6 657.4H866C860.5 657.4 856.1 656.5 852.8 654.7 849.4 652.9 846.2 649.9 843.2 645.8L733.6 452.2C733.3 456.2 733 460.1 732.7 463.8 732.3 467.6 732 471.1 731.7 474.4L710.2 657.4H648.2L686.9 343.7H723.9C726.9 343.7 729.5 343.8 731.6 344 733.7 344.2 735.5 344.7 737.1 345.5 738.7 346.3 740.1 347.4 741.4 348.8S744.1 352.1 745.5 354.4L855.5 548.1C855.8 543.1 856.2 538.3 856.7 533.7 857.2 529.2 857.8 524.8 858.3 520.8L879.4 343.6H941.4L902.6 657.4Z",
338 "width": 1000
339 },
340 "search": [
341 "svn"
342 ]
343 },
344 {
345 "uid": "bbfb51903f40597f0b70fd75bc7b5cac",
346 "css": "trash",
347 "code": 61944,
348 "src": "fontawesome"
349 },
350 {
351 "uid": "f48ae54adfb27d8ada53d0fd9e34ee10",
352 "css": "trash-empty",
353 "code": 59406,
354 "src": "fontawesome"
355 },
356 {
357 "uid": "f8aa663c489bcbd6e68ec8147dca841e",
358 "css": "folder",
359 "code": 59404,
360 "src": "fontawesome"
361 },
362 {
363 "uid": "c8585e1e5b0467f28b70bce765d5840c",
364 "css": "docs",
365 "code": 61637,
366 "src": "fontawesome"
367 },
368 {
369 "uid": "1b5a5d7b7e3c71437f5a26befdd045ed",
370 "css": "doc",
371 "code": 59414,
372 "src": "fontawesome"
373 },
374 {
375 "uid": "5408be43f7c42bccee419c6be53fdef5",
376 "css": "doc-text",
377 "code": 61686,
378 "src": "fontawesome"
379 },
380 {
381 "uid": "b091a8bd0fdade174951f17d936f51e4",
382 "css": "folder-empty",
383 "code": 61716,
384 "src": "fontawesome"
385 },
386 {
387 "uid": "c08a1cde48d96cba21d8c05fa7d7feb1",
388 "css": "doc-text-inv",
389 "code": 61788,
390 "src": "fontawesome"
391 },
392 {
393 "uid": "178053298e3e5b03551d754d4b9acd8b",
394 "css": "doc-inv",
395 "code": 61787,
396 "src": "fontawesome"
397 },
398 {
399 "uid": "e99461abfef3923546da8d745372c995",
400 "css": "cog",
401 "code": 59415,
402 "src": "fontawesome"
403 },
404 {
405 "uid": "98687378abd1faf8f6af97c254eb6cd6",
406 "css": "cog-alt",
407 "code": 59416,
408 "src": "fontawesome"
409 },
410 {
411 "uid": "21b42d3c3e6be44c3cc3d73042faa216",
412 "css": "sliders",
413 "code": 61918,
414 "src": "fontawesome"
415 },
416 {
417 "uid": "559647a6f430b3aeadbecd67194451dd",
418 "css": "menu",
419 "code": 61641,
420 "src": "fontawesome"
421 },
422 {
423 "uid": "c5fd349cbd3d23e4ade333789c29c729",
424 "css": "eye",
425 "code": 59417,
426 "src": "fontawesome"
427 },
428 {
429 "uid": "7fd683b2c518ceb9e5fa6757f2276faa",
430 "css": "eye-off",
431 "code": 59418,
432 "src": "fontawesome"
433 },
434 {
435 "uid": "2e2dba0307a502a8507c1729084c7ab5",
436 "css": "cancel-circled2",
437 "code": 59419,
438 "src": "fontawesome"
439 },
440 {
441 "uid": "0f4cae16f34ae243a6144c18a003f2d8",
442 "css": "cancel-circled",
443 "code": 59420,
444 "src": "fontawesome"
445 },
446 {
447 "uid": "26613a2e6bc41593c54bead46f8c8ee3",
448 "css": "file-code",
449 "code": 61897,
450 "src": "fontawesome"
451 },
452 {
453 "uid": "5211af474d3a9848f67f945e2ccaf143",
454 "css": "remove",
455 "code": 59408,
456 "src": "fontawesome"
457 },
458 {
459 "uid": "44e04715aecbca7f266a17d5a7863c68",
460 "css": "plus",
461 "code": 59421,
462 "src": "fontawesome"
463 },
464 {
465 "uid": "4ba33d2607902cf690dd45df09774cb0",
466 "css": "plus-circled",
467 "code": 59422,
468 "src": "fontawesome"
469 },
470 {
471 "uid": "1a5cfa186647e8c929c2b17b9fc4dac1",
472 "css": "plus-squared",
473 "code": 61694,
474 "src": "fontawesome"
475 },
476 {
477 "uid": "2d3be3e856fc1e4ac067590d2ded1b07",
478 "css": "plus-squared-alt",
479 "code": 61846,
480 "src": "fontawesome"
481 },
482 {
483 "uid": "eeadb020bb75d089b25d8424aabe19e0",
484 "css": "minus-circled",
485 "code": 59423,
486 "src": "fontawesome"
487 },
488 {
489 "uid": "f755a58fb985eeb70bd47d9b31892a34",
490 "css": "minus-squared",
491 "code": 61766,
492 "src": "fontawesome"
493 },
494 {
495 "uid": "18ef25350258541e8e54148ed79845c0",
496 "css": "minus-squared-alt",
497 "code": 61767,
498 "src": "fontawesome"
499 },
500 {
501 "uid": "861ab06e455e2de3232ebef67d60d708",
502 "css": "minus",
503 "code": 59424,
504 "src": "fontawesome"
505 },
506 {
507 "uid": "e82cedfa1d5f15b00c5a81c9bd731ea2",
508 "css": "info-circled",
509 "code": 59425,
510 "src": "fontawesome"
511 },
512 {
513 "uid": "9dd9e835aebe1060ba7190ad2b2ed951",
514 "css": "search",
515 "code": 59411,
516 "src": "fontawesome"
517 },
518 {
519 "uid": "b429436ec5a518c78479d44ef18dbd60",
520 "css": "paste",
521 "code": 61674,
522 "src": "fontawesome"
523 },
524 {
525 "uid": "8772331a9fec983cdb5d72902a6f9e0e",
526 "css": "scissors",
527 "code": 59412,
528 "src": "fontawesome"
529 },
530 {
531 "uid": "9a76bc135eac17d2c8b8ad4a5774fc87",
532 "css": "download",
533 "code": 59413,
534 "src": "fontawesome"
535 },
536 {
537 "uid": "eeec3208c90b7b48e804919d0d2d4a41",
538 "css": "upload",
539 "code": 59426,
540 "src": "fontawesome"
541 },
542 {
543 "uid": "5d2d07f112b8de19f2c0dbfec3e42c05",
544 "css": "spin",
545 "code": 59448,
546 "src": "fontelico"
547 },
548 {
549 "uid": "9bd60140934a1eb9236fd7a8ab1ff6ba",
550 "css": "spin-alt",
551 "code": 59444,
552 "src": "fontelico"
553 },
554 {
555 "uid": "513ac180ff85bd275f2b736720cbbf5e",
556 "css": "home",
557 "code": 59427,
558 "src": "entypo"
559 },
560 {
561 "uid": "d4816c0845aa43767213d45574b3b145",
562 "css": "history",
563 "code": 61914,
564 "src": "fontawesome"
565 },
566 {
567 "uid": "c43db6645e7515889fc2193294f50767",
568 "css": "plus",
569 "code": 59411,
570 "src": "custom_icons",
571 "selected": false,
572 "svg": {
573 "path": "M873.1 446.2H619.2C603.8 446.2 592.3 434.6 592.3 419.2V165.4C592.3 150 580.8 138.5 565.4 138.5H465.4C450 138.5 438.5 150 438.5 165.4V419.2C438.5 434.6 426.9 446.2 411.5 446.2H157.7C142.3 446.2 130.8 457.7 130.8 473.1V573.1C130.8 588.5 142.3 600 157.7 600H411.5C426.9 600 438.5 611.5 438.5 626.9V880.8C438.5 896.2 450 907.7 465.4 907.7H565.4C580.8 907.7 592.3 896.2 592.3 880.8V626.9C592.3 611.5 603.8 600 619.2 600H873.1C888.5 600 900 588.5 900 573.1V473.1C900 457.7 888.5 446.2 873.1 446.2Z",
574 "width": 1000
575 },
576 "search": [
577 "plus"
578 ]
579 },
580 {
581 "uid": "7d7f338d90203f20c0d8d5c26091cc69",
582 "css": "minus",
583 "code": 59412,
584 "src": "custom_icons",
585 "selected": false,
586 "svg": {
587 "path": "M980 560H20C10 560 0 550 0 540V380C0 370 10 360 20 360H985C995 360 1005 370 1005 380V545C1000 550 990 560 980 560Z",
588 "width": 1000
589 },
590 "search": [
591 "minus"
592 ]
593 },
594 {
595 "uid": "4ccc61480001600f2e7e3c7dd0546c6e",
596 "css": "remove",
597 "code": 59413,
598 "src": "custom_icons",
599 "selected": false,
600 "svg": {
601 "path": "M975 140L860 25C845 10 825 10 810 25L525 310C510 325 490 325 475 310L190 25C175 10 155 10 140 25L25 140C10 155 10 175 25 190L310 475C325 490 325 510 310 525L25 810C10 825 10 845 25 860L140 975C155 990 175 990 190 975L475 690C490 675 510 675 525 690L810 975C825 990 845 990 860 975L975 860C990 845 990 825 975 810L690 525C675 510 675 490 690 475L975 190C990 180 990 155 975 140Z",
602 "width": 1000
603 },
604 "search": [
605 "remove"
606 ]
607 },
608 {
609 "uid": "b1afcccc053ecb95fbcacf06e5c0d554",
610 "css": "history",
611 "code": 59418,
612 "src": "custom_icons",
613 "selected": false,
614 "svg": {
615 "path": "",
616 "width": 1143
617 },
618 "search": [
619 "history"
620 ]
621 }
622 ]
623 } No newline at end of file
@@ -0,0 +1,78 b''
1
2 How To Build A New Icon Font
3 ============================
4
5 Welcome. Contained in this repo is everything you need to build a new custom
6 RhodeCode icon font for RhodeCode Community and Enterprise Editions. While the
7 files are here, this document references what needs to be done in the actual
8 Community Edition repository.
9
10 Creating New Icons
11 ------------------
12
13 Presumably, you're reading this because you'd like to update the icon font with
14 new icons. To create new icons, you'll want to use Illustrator. Start with an
15 empty 1000px x 1000px artboard, or use an existing .svg file if you'd like to
16 use an existing icon as a guide.
17
18 You'll need to make sure that your outlines are paths. This can be done using
19 the Shape Modes in the Pathfinder tool; see Window > Pathfinder in Illustrator
20 to build a compound image. It may happen that your image is rasterized, in which
21 case it will need to be converted to vector; check the results carefully.
22
23 .. note::
24 When adding to the existing icon collection, please maintain our
25 existing icon style.
26
27
28 Creating The Font
29 -----------------
30
31 *Fontello*
32
33 We use fontello.com to generate the font files. On the main page, there is a
34 section for clicking and dragging icons to add to a font. If you would like to
35 use the existing font icons, here you will need to drag the .json file from the
36 current fontello folder. Once it has preloaded all of the existing fonts, drag
37 any new .svg icons into this same section to add them.
38
39 Any icons which appear blank or incorrect will need to be rebuilt in Illustrator.
40 This likely means that the paths have not been generated correctly; check the
41 settings in the Pathfinder tool.
42
43 After all of the icons are loaded into fontello, resist the temptation to click
44 the big red button; there's another task to do. Each icon has a pencil button;
45 click *every* icon - including the pre-existing ones - and check the settings.
46 Each current icon should have the same hex code as that which is listed in
47 rcicons.less. The "default css name" should be its simplified name; this is what
48 will be prepended with "icon-" for the CSS classes. Also remove any unnecessary
49 information from the keywords.
50
51 Once you have checked the icons, click the button in fontello which downloads a
52 zip file of the new font.
53
54
55 Preparing The LESS Files
56 ------------------------
57
58 .. note::
59 It's a good idea to have `grunt watch` running in the background for this.
60
61 First, obviously the font files located in the unzipped folder under "font"
62 should replace the existing files in rhodecode/public/fonts/RCIcons/. While
63 doing this, check the permissions of the files that they have not changed; they
64 should be set to `chmod 644` but fontello's files may be different.
65
66 Next, you'll need to open the rcicons.css file which comes in the fontello .zip
67 and match the @font-face declaration to the one at the top of
68 rhodecode/public/css/rcicons.less, making sure to adjust the paths to
69 /fonts/RCIcons/.
70
71 In the same file, you will see the CSS for each icon. Take a quick look to make
72 sure that the existing icons haven't changed; if they have, you'll need to
73 adjust the content. Add any new icons to rcicons.less (note that similar ones
74 have been grouped together).
75
76 If you haven't yet, you'll need to run grunt to compile the LESS files; see the
77 developer documentation for instructions.
78
@@ -0,0 +1,52 b''
1 ## -*- coding: utf-8 -*-
2 <%inherit file="/base/base.mako"/>
3
4 <%def name="title()">
5 ${_('Integrations administration')}
6 %if c.rhodecode_name:
7 &middot; ${h.branding(c.rhodecode_name)}
8 %endif
9 </%def>
10
11 <%def name="breadcrumbs_links()">
12 ${h.link_to(_('Admin'),h.route_path('admin_home'))}
13 &raquo;
14 ${_('Integrations')}
15 </%def>
16
17 <%def name="menu_bar_nav()">
18 ${self.menu_items(active='admin')}
19 </%def>
20
21 <%def name="menu_bar_subnav()">
22 ${self.admin_menu(active='integrations')}
23 </%def>
24
25 <%def name="side_bar_nav()">
26 <li class="active">
27 <a href="${h.route_path('global_integrations_home')}">Global</a>
28 </li>
29 </%def>
30
31 <%def name="main_content()">
32 <%include file="/admin/settings/settings_${c.active}.mako"/>
33 </%def>
34
35 <%def name="main()">
36 <div class="box">
37
38 ##main
39 <div class='sidebar-col-wrapper'>
40 <div class="sidebar">
41 <ul class="nav nav-pills nav-stacked">
42 ${self.side_bar_nav()}
43 </ul>
44 </div>
45
46 <div class="main-content-auto-width">
47 ${self.main_content()}
48 </div>
49 </div>
50 </div>
51
52 </%def>
@@ -0,0 +1,68 b''
1 ## -*- coding: utf-8 -*-
2 <%inherit file="/base/base.mako"/>
3
4 <%def name="title()">
5 ${_('Settings administration')}
6 %if c.rhodecode_name:
7 &middot; ${h.branding(c.rhodecode_name)}
8 %endif
9 </%def>
10
11 <%def name="breadcrumbs_links()"></%def>
12
13 <%def name="menu_bar_nav()">
14 ${self.menu_items(active='admin')}
15 </%def>
16
17 <%def name="menu_bar_subnav()">
18 ${self.admin_menu()}
19 </%def>
20
21 <%def name="side_bar_nav()">
22
23 </%def>
24
25 <%def name="main_content()">
26 <h2>${_('Administration area')}</h2>
27
28 <table class="rctable">
29 <tr>
30 <td>${_('Repositories under administration')}</td>
31 <td class="delegated-admin-repos">${len(c.auth_user.repositories_admin)}</td>
32 <td>
33 % if c.can_create_repo:
34 <a href="${h.route_path('repo_new')}" class="">${_('Add Repository')}</a>
35 % endif
36 </td>
37 </tr>
38 <tr>
39 <td>${_('Repository groups under administration')}</td>
40 <td class="delegated-admin-repo-groups">${len(c.auth_user.repository_groups_admin)}</td>
41 <td>
42 % if c.can_create_repo_group:
43 <a href="${h.route_path('repo_group_new')}" class="">${_(u'Add Repository Group')}</a>
44 % endif
45 </td>
46 </tr>
47 <tr>
48 <td>${_('User groups under administration')}</td>
49 <td class="delegated-admin-user-groups">${len(c.auth_user.user_groups_admin)}</td>
50 <td>
51 % if c.can_create_user_group:
52 <a href="${h.route_path('user_groups_new')}" class="">${_(u'Add User Group')}</a>
53 % endif
54 </td>
55 </tr>
56 </table>
57 </%def>
58
59 <%def name="main()">
60 <div class="box">
61
62 ##main
63 <div class="main-content-auto-width">
64 ${self.main_content()}
65 </div>
66 </div>
67
68 </%def> No newline at end of file
@@ -0,0 +1,28 b''
1 ## -*- coding: utf-8 -*-
2 <%inherit file="/base/base.mako"/>
3
4 <%def name="title()">
5 ${_('{} Artifacts').format(c.repo_name)}
6 %if c.rhodecode_name:
7 &middot; ${h.branding(c.rhodecode_name)}
8 %endif
9 </%def>
10
11 <%def name="breadcrumbs_links()"></%def>
12
13 <%def name="menu_bar_nav()">
14 ${self.menu_items(active='repositories')}
15 </%def>
16
17 <%def name="menu_bar_subnav()">
18 ${self.repo_menu(active='artifacts')}
19 </%def>
20
21 <%def name="main()">
22 <div class="box">
23
24 <h4>${_('This feature is available in RhodeCode EE edition only. Contact {sales_email} to obtain a trial license.').format(sales_email='<a href="mailto:sales@rhodecode.com">sales@rhodecode.com</a>')|n}</h4>
25 ##<img style="width: 100%; height: 100%" src="${h.asset('images/ee_features/repo_artifacts.png')}"/>
26 </div>
27
28 </%def>
@@ -0,0 +1,9 b''
1 <%namespace name="sourceblock" file="/codeblocks/source.mako"/>
2
3 <%def name="render_lines(lines)">
4 <table class="cb codehilite">
5 %for line_num, tokens in enumerate(lines, 1):
6 ${sourceblock.render_line(line_num, tokens)}
7 %endfor
8 </table>
9 </%def>
@@ -0,0 +1,211 b''
1 <%inherit file="/base/base.mako"/>
2
3 <%def name="title()">
4 ${_('{} Files Upload').format(c.repo_name)}
5 %if c.rhodecode_name:
6 &middot; ${h.branding(c.rhodecode_name)}
7 %endif
8 </%def>
9
10 <%def name="menu_bar_nav()">
11 ${self.menu_items(active='repositories')}
12 </%def>
13
14 <%def name="breadcrumbs_links()"></%def>
15
16 <%def name="menu_bar_subnav()">
17 ${self.repo_menu(active='files')}
18 </%def>
19
20 <%def name="main()">
21
22 <div class="box">
23 ## Template for uploads
24 <div style="display: none" id="tpl-dropzone">
25 <div class="dz-preview dz-file-preview">
26 <div class="dz-details">
27
28 <div class="dz-filename">
29 <span data-dz-name></span>
30 </div>
31 <div class="dz-filename-size">
32 <span class="dz-size" data-dz-size></span>
33
34 </div>
35
36 <div class="dz-sending" style="display: none">${_('Uploading...')}</div>
37 <div class="dz-response" style="display: none">
38 ${_('Uploaded')} 100%
39 </div>
40
41 </div>
42 <div class="dz-progress">
43 <span class="dz-upload" data-dz-uploadprogress></span>
44 </div>
45
46 <div class="dz-error-message">
47 </div>
48 </div>
49 </div>
50
51 <div class="edit-file-title">
52 <span class="title-heading">${_('Upload new file')} @ <code>${h.show_id(c.commit)}</code></span>
53 % if c.commit.branch:
54 <span class="tag branchtag">
55 <i class="icon-branch"></i> ${c.commit.branch}
56 </span>
57 % endif
58 </div>
59
60 <% form_url = h.route_path('repo_files_upload_file', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path) %>
61 ##${h.secure_form(form_url, id='eform', enctype="multipart/form-data", request=request)}
62 <div class="edit-file-fieldset">
63 <div class="path-items">
64 <ul>
65 <li class="breadcrumb-path">
66 <div>
67 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path='')}"><i class="icon-home"></i></a> /
68 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path)}">${c.f_path}</a> ${('/' if c.f_path else '')}
69 </div>
70 </li>
71 <li class="location-path">
72
73 </li>
74 </ul>
75 </div>
76
77 </div>
78
79 <div class="upload-form table">
80 <div id="files_data">
81
82 <div class="dropzone-wrapper" id="file-uploader">
83 <div class="dropzone-pure">
84 <div class="dz-message">
85 <i class="icon-upload" style="font-size:36px"></i></br>
86 ${_("Drag'n Drop files here or")} <span class="link">${_('Choose your files')}</span>.<br>
87 </div>
88 </div>
89
90 </div>
91 </div>
92
93 </div>
94
95 <div class="upload-form edit-file-fieldset">
96 <div class="fieldset">
97 <div class="message">
98 <textarea id="commit" name="message" placeholder="${c.default_message}"></textarea>
99 </div>
100 </div>
101 <div class="pull-left">
102 ${h.submit('commit_btn',_('Commit changes'), class_="btn btn-small btn-success")}
103 </div>
104 </div>
105 ##${h.end_form()}
106
107 <div class="file-upload-transaction-wrapper" style="display: none">
108 <div class="file-upload-transaction">
109 <h3>${_('Commiting...')}</h3>
110 <p>${_('Please wait while the files are being uploaded')}</p>
111 <p class="error" style="display: none">
112
113 </p>
114 <i class="icon-spin animate-spin"></i>
115 <p></p>
116 </div>
117 </div>
118
119 </div>
120
121 <script type="text/javascript">
122
123 $(document).ready(function () {
124
125 //see: https://www.dropzonejs.com/#configuration
126 myDropzone = new Dropzone("div#file-uploader", {
127 url: "${form_url}",
128 headers: {"X-CSRF-Token": CSRF_TOKEN},
129 paramName: function () {
130 return "files_upload"
131 }, // The name that will be used to transfer the file
132 parallelUploads: 20,
133 maxFiles: 20,
134 uploadMultiple: true,
135 //chunking: true, // use chunking transfer, not supported at the moment
136 //maxFilesize: 2, // in MBs
137 autoProcessQueue: false, // if false queue will not be processed automatically.
138 createImageThumbnails: false,
139 previewTemplate: document.querySelector('#tpl-dropzone').innerHTML,
140 accept: function (file, done) {
141 done();
142 },
143 init: function () {
144 this.on("addedfile", function (file) {
145
146 });
147
148 this.on("sending", function (file, xhr, formData) {
149 formData.append("message", $('#commit').val());
150 $(file.previewElement).find('.dz-sending').show();
151 });
152
153 this.on("success", function (file, response) {
154 $(file.previewElement).find('.dz-sending').hide();
155 $(file.previewElement).find('.dz-response').show();
156
157 if (response.error !== null) {
158 $('.file-upload-transaction-wrapper .error').html('ERROR: {0}'.format(response.error));
159 $('.file-upload-transaction-wrapper .error').show();
160 $('.file-upload-transaction-wrapper i').hide()
161 }
162
163 var redirect_url = response.redirect_url || '/';
164 window.location = redirect_url
165
166 });
167
168 this.on("error", function (file, errorMessage, xhr) {
169 var error = null;
170
171 if (xhr !== undefined){
172 var httpStatus = xhr.status + " " + xhr.statusText;
173 if (xhr.status >= 500) {
174 error = httpStatus;
175 }
176 }
177
178 if (error === null) {
179 error = errorMessage.error || errorMessage || httpStatus;
180 }
181
182 $(file.previewElement).find('.dz-error-message').html('ERROR: {0}'.format(error));
183 });
184 }
185 });
186
187 $('#commit_btn').on('click', function(e) {
188 e.preventDefault();
189 var button = $(this);
190 if (button.hasClass('clicked')) {
191 button.attr('disabled', true);
192 } else {
193 button.addClass('clicked');
194 }
195
196 var files = myDropzone.getQueuedFiles();
197 if (files.length === 0) {
198 alert("Missing files");
199 e.preventDefault();
200 }
201
202 $('.upload-form').hide();
203 $('.file-upload-transaction-wrapper').show();
204 myDropzone.processQueue();
205
206 });
207
208 });
209
210 </script>
211 </%def>
@@ -1,5 +1,5 b''
1 1 [bumpversion]
2 current_version = 4.16.2
2 current_version = 4.17.0
3 3 message = release: Bump version {current_version} to {new_version}
4 4
5 5 [bumpversion:file:rhodecode/VERSION]
@@ -5,25 +5,20 b' done = false'
5 5 done = true
6 6
7 7 [task:rc_tools_pinned]
8 done = true
9 8
10 9 [task:fixes_on_stable]
11 done = true
12 10
13 11 [task:pip2nix_generated]
14 done = true
15 12
16 13 [task:changelog_updated]
17 done = true
18 14
19 15 [task:generate_api_docs]
20 done = true
16
17 [task:updated_translation]
21 18
22 19 [release]
23 state = prepared
24 version = 4.16.2
25
26 [task:updated_translation]
20 state = in_progress
21 version = 4.17.0
27 22
28 23 [task:generate_js_routes]
29 24
@@ -53,3 +53,12 b' web-build:'
53 53
54 54 generate-pkgs:
55 55 nix-shell pkgs/shell-generate.nix --command "pip2nix generate --licenses"
56
57 generate-js-pkgs:
58 rm -rf node_modules && \
59 nix-shell pkgs/shell-generate.nix --command "node2nix --input package.json -o pkgs/node-packages.nix -e pkgs/node-env.nix -c pkgs/node-default.nix -d --flatten --nodejs-8" && \
60 sed -i -e 's/http:\/\//https:\/\//g' pkgs/node-packages.nix
61
62 generate-license-meta:
63 nix-build pkgs/license-generate.nix -o result-license && \
64 cat result-license/licenses.json | python -m json.tool > rhodecode/config/licenses.json No newline at end of file
@@ -133,6 +133,11 b' rhodecode.api.url = /_admin/api'
133 133 ## `SignatureVerificationError` in case of wrong key, or damaged encryption data.
134 134 #rhodecode.encrypted_values.strict = false
135 135
136 ## Pick algorithm for encryption. Either fernet (more secure) or aes (default)
137 ## fernet is safer, and we strongly recommend switching to it.
138 ## Due to backward compatibility aes is used as default.
139 #rhodecode.encrypted_values.algorithm = fernet
140
136 141 ## return gzipped responses from RhodeCode (static files/application)
137 142 gzip_responses = false
138 143
@@ -374,6 +379,10 b' rc_cache.cache_repo_longterm.max_size = '
374 379 beaker.session.type = file
375 380 beaker.session.data_dir = %(here)s/data/sessions
376 381
382 ## redis sessions
383 #beaker.session.type = ext:redis
384 #beaker.session.url = redis://127.0.0.1:6379/2
385
377 386 ## db based session, fast, and allows easy management over logged in users
378 387 #beaker.session.type = ext:database
379 388 #beaker.session.table_name = db_session
@@ -30,10 +30,12 b" loglevel = 'debug'"
30 30 # SECURITY
31 31
32 32 # The maximum size of HTTP request line in bytes.
33 limit_request_line = 4094
33 # 0 for unlimited
34 limit_request_line = 0
34 35
35 36 # Limit the number of HTTP headers fields in a request.
36 limit_request_fields = 1024
37 # By default this value is 100 and can’t be larger than 32768.
38 limit_request_fields = 10240
37 39
38 40 # Limit the allowed size of an HTTP request header field.
39 41 # Value is a positive number or 0.
@@ -108,6 +108,11 b' use = egg:rhodecode-enterprise-ce'
108 108 ## `SignatureVerificationError` in case of wrong key, or damaged encryption data.
109 109 #rhodecode.encrypted_values.strict = false
110 110
111 ## Pick algorithm for encryption. Either fernet (more secure) or aes (default)
112 ## fernet is safer, and we strongly recommend switching to it.
113 ## Due to backward compatibility aes is used as default.
114 #rhodecode.encrypted_values.algorithm = fernet
115
111 116 ## return gzipped responses from RhodeCode (static files/application)
112 117 gzip_responses = false
113 118
@@ -349,6 +354,10 b' rc_cache.cache_repo_longterm.max_size = '
349 354 beaker.session.type = file
350 355 beaker.session.data_dir = %(here)s/data/sessions
351 356
357 ## redis sessions
358 #beaker.session.type = ext:redis
359 #beaker.session.url = redis://127.0.0.1:6379/2
360
352 361 ## db based session, fast, and allows easy management over logged in users
353 362 #beaker.session.type = ext:database
354 363 #beaker.session.table_name = db_session
@@ -191,7 +191,7 b' let'
191 191 # check required files
192 192 STATIC_CHECK="/robots.txt /502.html
193 193 /js/scripts.js /js/rhodecode-components.js
194 /css/style.css /css/style-polymer.css"
194 /css/style.css /css/style-polymer.css /css/style-ipython.css"
195 195
196 196 for file in $STATIC_CHECK;
197 197 do
@@ -29,7 +29,7 b' 1. Go to :menuselection:`Admin --> Repos'
29 29 beside the |repo| to which you wish to add extra fields.
30 30 2. On the |repo| settings page, select the :guilabel:`Extra fields` tab.
31 31
32 .. image:: ../images/extra-repo-fields.png
32 .. image:: ../../images/extra-repo-fields.png
33 33
34 34 The most important is the `New field key` variable which under the value will
35 35 be stored. It needs to be unique for each repository. The label and description
1 NO CONTENT: file renamed from docs/admin/repo-hooks.rst to docs/admin/repo_admin/repo-hooks.rst
1 NO CONTENT: file renamed from docs/admin/repo-issue-tracker.rst to docs/admin/repo_admin/repo-issue-tracker.rst
1 NO CONTENT: file renamed from docs/admin/repo-perm-steps.rst to docs/admin/repo_admin/repo-perm-steps.rst
1 NO CONTENT: file renamed from docs/admin/repo-vcs.rst to docs/admin/repo_admin/repo-vcs.rst
1 NO CONTENT: file renamed from docs/admin/restore-deleted-repositories.rst to docs/admin/repo_admin/restore-deleted-repositories.rst
@@ -16,19 +16,17 b' The following are the most common system'
16 16
17 17 .. toctree::
18 18
19 config-files-overview
20 vcs-server
21 svn-http
22 svn-path-permissions
23 gunicorn-ssl-support
24 apache-config
25 nginx-config
26 backup-restore
27 tuning-rhodecode
28 indexing
29 reset-information
30 enable-debug
31 admin-tricks
32 cleanup-cmds
33 restore-deleted-repositories
34
19 system_admin/config-files-overview
20 system_admin/vcs-server
21 system_admin/svn-http
22 system_admin/svn-path-permissions
23 system_admin/gunicorn-ssl-support
24 system_admin/apache-config
25 system_admin/nginx-config
26 system_admin/backup-restore
27 system_admin/tuning-rhodecode
28 system_admin/indexing
29 system_admin/reset-information
30 system_admin/enable-debug
31 system_admin/admin-tricks
32 system_admin/cleanup-cmds
@@ -57,7 +57,7 b' 2. To add a message that will be display'
57 57 3. Select :guilabel:`Save`, and you will see the message once your page
58 58 refreshes.
59 59
60 .. image:: ../images/server-wide-announcement.png
60 .. image:: ../../images/server-wide-announcement.png
61 61 :alt: Server Wide Announcement
62 62
63 63 .. _md-rst:
@@ -207,7 +207,7 b' 2. Restart the |RCE| instance and check '
207 207 Instance "enterprise-2" successfully stopped.
208 208 Instance "enterprise-2" successfully started.
209 209
210 .. image:: ../images/language.png
210 .. image:: ../../images/language.png
211 211
212 212 .. _set-repo-pub:
213 213
@@ -239,3 +239,26 b' following URL: ``{instance-URL}/_admin/p'
239 239
240 240 .. _Markdown: http://daringfireball.net/projects/markdown/
241 241 .. _reStructured Text: http://docutils.sourceforge.net/docs/index.html
242
243
244 Unarchiving a repository
245 ^^^^^^^^^^^^^^^^^^^^^^^^^
246
247 Archive operation for the repository is similar as delete. Archive keeps the data for future references
248 but makes the repository read-only. After archiving the repository it shouldn't be modified in any way.
249 This is why repository settings are disabled for an archived repository.
250
251 If there's a need for unarchiving a repository for some reasons, the interactive
252 ishell interface should be used.
253
254 .. code-block:: bash
255
256 # Open iShell from the terminal
257 $ rccontrol ishell enterprise-1/community-1
258
259 .. code-block:: python
260
261 # Set repository as un-archived
262 In [1]: repo = Repository.get_by_repo_name('SOME_REPO_NAME')
263 In [2]: repo.archived = False
264 In [3]: Session().add(repo);Session().commit()
@@ -8,7 +8,7 b' the information in the following section'
8 8
9 9 .. toctree::
10 10
11 apache-conf-example
12 apache-diffie-hellman
13 apache-subdirectory
14 apache-wsgi-coding
11 apache/apache-conf-example
12 apache/apache-diffie-hellman
13 apache/apache-subdirectory
14 apache/apache-wsgi-coding
@@ -66,14 +66,18 b' Below config if for an Apache Reverse Pr'
66 66 # Directive to properly generate url (clone url) for RhodeCode
67 67 ProxyPreserveHost On
68 68
69 # It allows request bodies to be sent to the backend using chunked transfer encoding.
70 SetEnv proxy-sendchunked 1
71
72 # Increase headers size for large Mercurial headers sent with many branches
73 LimitRequestLine 16380
74
69 75 # Url to running RhodeCode instance. This is shown as `- URL:` when
70 76 # running rccontrol status.
77
71 78 ProxyPass / http://127.0.0.1:10002/ timeout=7200 Keepalive=On
72 79 ProxyPassReverse / http://127.0.0.1:10002/
73 80
74 # Increase headers for large Mercurial headers
75 LimitRequestLine 16380
76
77 81 # strict http prevents from https -> http downgrade
78 82 Header always set Strict-Transport-Security "max-age=63072000; includeSubdomains; preload"
79 83
1 NO CONTENT: file renamed from docs/admin/apache-diffie-hellman.rst to docs/admin/system_admin/apache/apache-diffie-hellman.rst
1 NO CONTENT: file renamed from docs/admin/apache-subdirectory.rst to docs/admin/system_admin/apache/apache-subdirectory.rst
1 NO CONTENT: file renamed from docs/admin/apache-wsgi-coding.rst to docs/admin/system_admin/apache/apache-wsgi-coding.rst
1 NO CONTENT: file renamed from docs/admin/backup-restore.rst to docs/admin/system_admin/backup-restore.rst
1 NO CONTENT: file renamed from docs/admin/cleanup-cmds.rst to docs/admin/system_admin/cleanup-cmds.rst
1 NO CONTENT: file renamed from docs/admin/config-files-overview.rst to docs/admin/system_admin/config-files-overview.rst
1 NO CONTENT: file renamed from docs/admin/enable-debug.rst to docs/admin/system_admin/enable-debug.rst
1 NO CONTENT: file renamed from docs/admin/gunicorn-ssl-support.rst to docs/admin/system_admin/gunicorn-ssl-support.rst
1 NO CONTENT: file renamed from docs/admin/indexing.rst to docs/admin/system_admin/indexing.rst
@@ -8,7 +8,7 b' the information in the following section'
8 8
9 9 .. toctree::
10 10
11 nginx-config-example
12 nginx-diffie-hellman
13 nginx-proxy-conf
14 nginx-url-prefix
11 nginx/nginx-config-example
12 nginx/nginx-diffie-hellman
13 nginx/nginx-proxy-conf
14 nginx/nginx-url-prefix
1 NO CONTENT: file renamed from docs/admin/nginx-config-example.rst to docs/admin/system_admin/nginx/nginx-config-example.rst
1 NO CONTENT: file renamed from docs/admin/nginx-diffie-hellman.rst to docs/admin/system_admin/nginx/nginx-diffie-hellman.rst
1 NO CONTENT: file renamed from docs/admin/nginx-proxy-conf.rst to docs/admin/system_admin/nginx/nginx-proxy-conf.rst
1 NO CONTENT: file renamed from docs/admin/nginx-url-prefix.rst to docs/admin/system_admin/nginx/nginx-url-prefix.rst
1 NO CONTENT: file renamed from docs/admin/reset-information.rst to docs/admin/system_admin/reset-information.rst
1 NO CONTENT: file renamed from docs/admin/svn-http.rst to docs/admin/system_admin/svn-http.rst
1 NO CONTENT: file renamed from docs/admin/svn-path-permissions.rst to docs/admin/system_admin/svn-path-permissions.rst
@@ -8,14 +8,14 b' may find some of the following methods u'
8 8
9 9 .. toctree::
10 10
11 tuning-gunicorn
12 tuning-vcs-memory-cache
13 tuning-user-sessions-performance
14 tuning-increase-db-performance
15 tuning-scale-horizontally-cluster
16 tuning-mount-cache-memory
17 tuning-change-encoding
18 tuning-change-large-file-dir
19 tuning-change-lfs-dir
20 tuning-hg-auth-loop
11 tuning/tuning-gunicorn
12 tuning/tuning-vcs-memory-cache
13 tuning/tuning-user-sessions-performance
14 tuning/tuning-increase-db-performance
15 tuning/tuning-scale-horizontally-cluster
16 tuning/tuning-mount-cache-memory
17 tuning/tuning-change-encoding
18 tuning/tuning-change-large-file-dir
19 tuning/tuning-change-lfs-dir
20 tuning/tuning-hg-auth-loop
21 21
1 NO CONTENT: file renamed from docs/admin/tuning-change-encoding.rst to docs/admin/system_admin/tuning/tuning-change-encoding.rst
1 NO CONTENT: file renamed from docs/admin/tuning-change-large-file-dir.rst to docs/admin/system_admin/tuning/tuning-change-large-file-dir.rst
1 NO CONTENT: file renamed from docs/admin/tuning-change-lfs-dir.rst to docs/admin/system_admin/tuning/tuning-change-lfs-dir.rst
@@ -42,7 +42,7 b' 2. In the ``[server:main]`` section, cha'
42 42 ## restarted, could prevent memory leaks
43 43 max_requests = 1000
44 44 max_requests_jitter = 30
45 ## amount of time a worker can spend with handling a request before it
45 ## amount of time a worker can spend with handling a request tuning-change-lfs-dir.before it
46 46 ## gets killed and restarted. Set to 6hrs
47 47 timeout = 21600
48 48
1 NO CONTENT: file renamed from docs/admin/tuning-hg-auth-loop.rst to docs/admin/system_admin/tuning/tuning-hg-auth-loop.rst
1 NO CONTENT: file renamed from docs/admin/tuning-increase-db-performance.rst to docs/admin/system_admin/tuning/tuning-increase-db-performance.rst
1 NO CONTENT: file renamed from docs/admin/tuning-mount-cache-memory.rst to docs/admin/system_admin/tuning/tuning-mount-cache-memory.rst
1 NO CONTENT: file renamed from docs/admin/tuning-scale-horizontally-cluster.rst to docs/admin/system_admin/tuning/tuning-scale-horizontally-cluster.rst
1 NO CONTENT: file renamed from docs/admin/tuning-user-sessions-performance.rst to docs/admin/system_admin/tuning/tuning-user-sessions-performance.rst
1 NO CONTENT: file renamed from docs/admin/tuning-vcs-memory-cache.rst to docs/admin/system_admin/tuning/tuning-vcs-memory-cache.rst
1 NO CONTENT: file renamed from docs/admin/vcs-server.rst to docs/admin/system_admin/vcs-server.rst
@@ -13,11 +13,12 b' permissions applied to it; |perm|.'
13 13
14 14 .. toctree::
15 15
16 public-access
17 default-user-perms
18 adding-anonymous-user
19 adding-new-user
20 setting-default-permissions
21 setting-usergroup-permissions
16 user_admin/public-access
17 user_admin/default-user-perms
18 user_admin/adding-anonymous-user
19 user_admin/adding-new-user
20 user_admin/setting-default-permissions
21 user_admin/setting-usergroup-permissions
22 user_admin/user-admin-tasks
22 23
23 .. |perm| replace:: **None**, **Read**, **Write**, or **Admin** No newline at end of file
24 .. |perm| replace:: **None**, **Read**, **Write**, or **Admin**
1 NO CONTENT: file renamed from docs/admin/adding-anonymous-user.rst to docs/admin/user_admin/adding-anonymous-user.rst
1 NO CONTENT: file renamed from docs/admin/adding-new-user.rst to docs/admin/user_admin/adding-new-user.rst
1 NO CONTENT: file renamed from docs/admin/default-user-perms.rst to docs/admin/user_admin/default-user-perms.rst
1 NO CONTENT: file renamed from docs/admin/public-access.rst to docs/admin/user_admin/public-access.rst
1 NO CONTENT: file renamed from docs/admin/setting-default-permissions.rst to docs/admin/user_admin/setting-default-permissions.rst
1 NO CONTENT: file renamed from docs/admin/setting-usergroup-permissions.rst to docs/admin/user_admin/setting-usergroup-permissions.rst
@@ -204,6 +204,7 b' are not required in args.'
204 204 methods/pull-request-methods
205 205 methods/repo-methods
206 206 methods/repo-group-methods
207 methods/search-methods
207 208 methods/server-methods
208 209 methods/user-methods
209 210 methods/user-group-methods
@@ -462,6 +462,7 b' get_repo_file'
462 462 :param cache: Use internal caches for fetching files. If disabled fetching
463 463 files is slower but more memory efficient
464 464 :type cache: Optional(bool)
465
465 466 Example output:
466 467
467 468 .. code-block:: bash
@@ -499,53 +500,51 b' get_repo_nodes'
499 500 .. py:function:: get_repo_nodes(apiuser, repoid, revision, root_path, ret_type=<Optional:'all'>, details=<Optional:'basic'>, max_file_bytes=<Optional:None>)
500 501
501 502 Returns a list of nodes and children in a flat list for a given
502 path at given revision.
503 path at given revision.
503 504
504 It's possible to specify ret_type to show only `files` or `dirs`.
505 It's possible to specify ret_type to show only `files` or `dirs`.
505 506
506 This command can only be run using an |authtoken| with admin rights,
507 or users with at least read rights to |repos|.
507 This command can only be run using an |authtoken| with admin rights,
508 or users with at least read rights to |repos|.
508 509
509 :param apiuser: This is filled automatically from the |authtoken|.
510 :type apiuser: AuthUser
511 :param repoid: The repository name or repository ID.
512 :type repoid: str or int
513 :param revision: The revision for which listing should be done.
514 :type revision: str
515 :param root_path: The path from which to start displaying.
516 :type root_path: str
517 :param ret_type: Set the return type. Valid options are
518 ``all`` (default), ``files`` and ``dirs``.
519 :type ret_type: Optional(str)
520 :param details: Returns extended information about nodes, such as
521 md5, binary, and or content.
522 The valid options are ``basic`` and ``full``.
523 :type details: Optional(str)
524 :param max_file_bytes: Only return file content under this file size bytes
525 :type details: Optional(int)
526
527 Example output:
510 :param apiuser: This is filled automatically from the |authtoken|.
511 :type apiuser: AuthUser
512 :param repoid: The repository name or repository ID.
513 :type repoid: str or int
514 :param revision: The revision for which listing should be done.
515 :type revision: str
516 :param root_path: The path from which to start displaying.
517 :type root_path: str
518 :param ret_type: Set the return type. Valid options are
519 ``all`` (default), ``files`` and ``dirs``.
520 :type ret_type: Optional(str)
521 :param details: Returns extended information about nodes, such as
522 md5, binary, and or content.
523 The valid options are ``basic`` and ``full``.
524 :type details: Optional(str)
525 :param max_file_bytes: Only return file content under this file size bytes
526 :type details: Optional(int)
528 527
529 .. code-block:: bash
528 Example output:
529
530 .. code-block:: bash
530 531
531 id : <id_given_in_input>
532 result: [
533 {
534 "binary": false,
535 "content": "File line
536 Line2
537 ",
538 "extension": "md",
539 "lines": 2,
540 "md5": "059fa5d29b19c0657e384749480f6422",
541 "mimetype": "text/x-minidsrc",
542 "name": "file.md",
543 "size": 580,
544 "type": "file"
545 },
546 ...
547 ]
548 error: null
532 id : <id_given_in_input>
533 result: [
534 {
535 "binary": false,
536 "content": "File line",
537 "extension": "md",
538 "lines": 2,
539 "md5": "059fa5d29b19c0657e384749480f6422",
540 "mimetype": "text/x-minidsrc",
541 "name": "file.md",
542 "size": 580,
543 "type": "file"
544 },
545 ...
546 ]
547 error: null
549 548
550 549
551 550 get_repo_refs
@@ -32,9 +32,9 b' The most important this id needs to be u'
32 32
33 33 In [1]: saml2user = {
34 34 ...: # OneLogin, uses externalID available to read from in the UI
35 ...: 123: {'id: '48253211'},
35 ...: 123: {'id': '48253211'},
36 36 ...: # for Google/DuoSecurity email is also an option for unique ID
37 ...: 124: {'id: 'email@domain.com'},
37 ...: 124: {'id': 'email@domain.com'},
38 38 ...: }
39 39
40 40
@@ -70,7 +70,7 b' Enter in the ishell prompt'
70 70 ...: new_external_identity.external_id = external_id
71 71 ...: new_external_identity.external_username = '{}-saml-{}'.format(user.username, user.user_id)
72 72 ...: new_external_identity.provider_name = provider
73 ...: new_external_identity.local_user_id = user_id
73 ...: new_external_identity.local_user_id = user.user_id
74 74 ...: new_external_identity.access_token = ''
75 75 ...: new_external_identity.token_secret = ''
76 76 ...: new_external_identity.alt_token = ''
@@ -46,7 +46,7 b' and commit files and |repos| while manag'
46 46 nix/default-env
47 47 admin/system-admin
48 48 admin/user-admin
49 admin/setting-repo-perms
49 admin/repo-admin
50 50 admin/security-tips
51 51 auth/auth
52 52 issue-trackers/issue-trackers
@@ -64,6 +64,13 b' and commit files and |repos| while manag'
64 64
65 65 .. toctree::
66 66 :maxdepth: 1
67 :caption: User Documentation
68
69 usage/basic-usage
70 tutorials/tutorials
71
72 .. toctree::
73 :maxdepth: 1
67 74 :caption: Developer Documentation
68 75
69 76 api/api
@@ -73,13 +80,6 b' and commit files and |repos| while manag'
73 80
74 81 .. toctree::
75 82 :maxdepth: 1
76 :caption: User Documentation
77
78 usage/basic-usage
79 tutorials/tutorials
80
81 .. toctree::
82 :maxdepth: 1
83 83 :caption: About
84 84
85 85 known-issues/known-issues
@@ -9,6 +9,7 b' Release Notes'
9 9 .. toctree::
10 10 :maxdepth: 1
11 11
12 release-notes-4.17.0.rst
12 13 release-notes-4.16.2.rst
13 14 release-notes-4.16.1.rst
14 15 release-notes-4.16.0.rst
@@ -35,6 +35,7 b''
35 35 "<%= dirs.js.node_modules %>/moment/min/moment.min.js",
36 36 "<%= dirs.js.node_modules %>/clipboard/dist/clipboard.min.js",
37 37 "<%= dirs.js.node_modules %>/favico.js/favico-0.3.10.min.js",
38 "<%= dirs.js.node_modules %>/dropzone/dist/dropzone.js",
38 39 "<%= dirs.js.node_modules %>/sticky-sidebar/dist/sticky-sidebar.min.js",
39 40 "<%= dirs.js.node_modules %>/sticky-sidebar/dist/jquery.sticky-sidebar.min.js",
40 41 "<%= dirs.js.node_modules %>/waypoints/lib/noframework.waypoints.min.js",
@@ -107,7 +108,8 b''
107 108 },
108 109 "files": {
109 110 "<%= dirs.css.dest %>/style.css": "<%= dirs.css.src %>/main.less",
110 "<%= dirs.css.dest %>/style-polymer.css": "<%= dirs.css.src %>/polymer.less"
111 "<%= dirs.css.dest %>/style-polymer.css": "<%= dirs.css.src %>/polymer.less",
112 "<%= dirs.css.dest %>/style-ipython.css": "<%= dirs.css.src %>/ipython.less"
111 113 }
112 114 },
113 115 "production": {
@@ -118,7 +120,8 b''
118 120 },
119 121 "files": {
120 122 "<%= dirs.css.dest %>/style.css": "<%= dirs.css.src %>/main.less",
121 "<%= dirs.css.dest %>/style-polymer.css": "<%= dirs.css.src %>/polymer.less"
123 "<%= dirs.css.dest %>/style-polymer.css": "<%= dirs.css.src %>/polymer.less",
124 "<%= dirs.css.dest %>/style-ipython.css": "<%= dirs.css.src %>/ipython.less"
122 125 }
123 126 },
124 127 "components": {
@@ -13,6 +13,7 b''
13 13 "clipboard": "^2.0.1",
14 14 "exports-loader": "^0.6.4",
15 15 "favico.js": "^0.3.10",
16 "dropzone": "^5.5.0",
16 17 "grunt": "^0.4.5",
17 18 "grunt-cli": "^1.3.1",
18 19 "grunt-contrib-concat": "^0.5.1",
@@ -1,3 +1,3 b''
1 1 [pip2nix]
2 requirements = ., -r ./requirements.txt
2 requirements = ., -r ./requirements.txt, -r ./requirements_pinned.txt
3 3 output = ./pkgs/python-packages.nix
This diff has been collapsed as it changes many lines, (990 lines changed) Show them Hide them
@@ -166,13 +166,13 b' let'
166 166 sha512 = "dgOe12GyCF1VZBLUQqnzGWlf3xb255FajNCVB1VFj/AtskYtoamnafa7m3a+1vs+C8qbg4Benn5KwgxVDSW4cg==";
167 167 };
168 168 };
169 "@polymer/paper-spinner-3.0.1" = {
169 "@polymer/paper-spinner-3.0.2" = {
170 170 name = "_at_polymer_slash_paper-spinner";
171 171 packageName = "@polymer/paper-spinner";
172 version = "3.0.1";
173 src = fetchurl {
174 url = "https://registry.npmjs.org/@polymer/paper-spinner/-/paper-spinner-3.0.1.tgz";
175 sha512 = "MYIU6qWZnhZ5yNFOBzROPgBteGfxKEnDZ6bCgjrvUtJkBuQEz0MQZzSE/zmZc0oaJ9u5QK5xAFuYdudsGv7+sQ==";
172 version = "3.0.2";
173 src = fetchurl {
174 url = "https://registry.npmjs.org/@polymer/paper-spinner/-/paper-spinner-3.0.2.tgz";
175 sha512 = "XUzu8/4NH+pnNZUTI2MxtOKFAr0EOsW7eGhTg3VBhTh7DDW/q3ewzwYRWnqNJokX9BEnxKMiXXaIeTEBq4k2dw==";
176 176 };
177 177 };
178 178 "@polymer/paper-styles-3.0.1" = {
@@ -211,13 +211,13 b' let'
211 211 sha512 = "yiUk09opTEnE1lK+tb501ENb+yQBi4p++Ep0eGJAHesVYKVMPNgPphVKkIizkDaU+n0SE+zXfTsRbYyOMDYXSg==";
212 212 };
213 213 };
214 "@polymer/polymer-3.1.0" = {
214 "@polymer/polymer-3.2.0" = {
215 215 name = "_at_polymer_slash_polymer";
216 216 packageName = "@polymer/polymer";
217 version = "3.1.0";
218 src = fetchurl {
219 url = "https://registry.npmjs.org/@polymer/polymer/-/polymer-3.1.0.tgz";
220 sha512 = "hwN8IMERsFATz/9dSMxYHL+84J9uBkPuuarxJWlTsppZ4CAYTZKnepBfNrKoyNsafBmA3yXBiiKPPf+fJtza7A==";
217 version = "3.2.0";
218 src = fetchurl {
219 url = "https://registry.npmjs.org/@polymer/polymer/-/polymer-3.2.0.tgz";
220 sha512 = "L6uV1oM6T6xbwbVx6t3biG5T2VSSB03LxnIrUd9M2pr6RkHVPFHJ37pC5MUwBAEhkGFJif7eks7fdMMSGZTeEQ==";
221 221 };
222 222 };
223 223 "@types/clone-0.1.30" = {
@@ -229,13 +229,13 b' let'
229 229 sha1 = "e7365648c1b42136a59c7d5040637b3b5c83b614";
230 230 };
231 231 };
232 "@types/node-6.14.2" = {
232 "@types/node-6.14.6" = {
233 233 name = "_at_types_slash_node";
234 234 packageName = "@types/node";
235 version = "6.14.2";
236 src = fetchurl {
237 url = "https://registry.npmjs.org/@types/node/-/node-6.14.2.tgz";
238 sha512 = "JWB3xaVfsfnFY8Ofc9rTB/op0fqqTSqy4vBcVk1LuRJvta7KTX+D//fCkiTMeLGhdr2EbFZzQjC97gvmPilk9Q==";
235 version = "6.14.6";
236 src = fetchurl {
237 url = "https://registry.npmjs.org/@types/node/-/node-6.14.6.tgz";
238 sha512 = "rFs9zCFtSHuseiNXxYxFlun8ibu+jtZPgRM+2ILCmeLiGeGLiIGxuOzD+cNyHegI1GD+da3R/cIbs9+xCLp13w==";
239 239 };
240 240 };
241 241 "@types/parse5-2.2.34" = {
@@ -409,22 +409,22 b' let'
409 409 sha512 = "mJ3QKWtCchL1vhU/kZlJnLPuQZnlDOdZsyP0bbLWPGdYsQDnSBvyTLhzwBA3QAMlzEL9V4JHygEmK6/OTEyytA==";
410 410 };
411 411 };
412 "@webcomponents/shadycss-1.7.1" = {
412 "@webcomponents/shadycss-1.9.1" = {
413 413 name = "_at_webcomponents_slash_shadycss";
414 414 packageName = "@webcomponents/shadycss";
415 version = "1.7.1";
416 src = fetchurl {
417 url = "https://registry.npmjs.org/@webcomponents/shadycss/-/shadycss-1.7.1.tgz";
418 sha512 = "6SZqLajRPWL0rrKDZOGF8PCBq5B9JqgFmE5rX5psk6i8WrqiMkSCuO8+rnirzViTsU5CqnjQPFC3OvG4YJdMrQ==";
419 };
420 };
421 "@webcomponents/webcomponentsjs-2.2.1" = {
415 version = "1.9.1";
416 src = fetchurl {
417 url = "https://registry.npmjs.org/@webcomponents/shadycss/-/shadycss-1.9.1.tgz";
418 sha512 = "IaZOnWOKXHghqk/WfPNDRIgDBi3RsVPY2IFAw6tYiL9UBGvQRy5R6uC+Fk7qTZsReTJ0xh5MTT8yAcb3MUR4mQ==";
419 };
420 };
421 "@webcomponents/webcomponentsjs-2.2.10" = {
422 422 name = "_at_webcomponents_slash_webcomponentsjs";
423 423 packageName = "@webcomponents/webcomponentsjs";
424 version = "2.2.1";
425 src = fetchurl {
426 url = "https://registry.npmjs.org/@webcomponents/webcomponentsjs/-/webcomponentsjs-2.2.1.tgz";
427 sha512 = "lZZ+Lkke6JhsJcQQqSVk1Pny6/8y4qhJ98LO7a/MwBSRO8WqHqK1X2vscfeL8vOnYGFnmBUyVG95lwYv/AXyLQ==";
424 version = "2.2.10";
425 src = fetchurl {
426 url = "https://registry.npmjs.org/@webcomponents/webcomponentsjs/-/webcomponentsjs-2.2.10.tgz";
427 sha512 = "5dzhUhP+h0qMiK0IWb7VNb0OGBoXO3AuI6Qi8t9PoKT50s5L1jv0xnwnLq+cFgPuTB8FLTNP8xIDmyoOsKBy9Q==";
428 428 };
429 429 };
430 430 "@xtuc/ieee754-1.2.0" = {
@@ -499,22 +499,22 b' let'
499 499 sha1 = "82ffb02b29e662ae53bdc20af15947706739c536";
500 500 };
501 501 };
502 "ajv-6.6.2" = {
502 "ajv-6.10.0" = {
503 503 name = "ajv";
504 504 packageName = "ajv";
505 version = "6.6.2";
506 src = fetchurl {
507 url = "https://registry.npmjs.org/ajv/-/ajv-6.6.2.tgz";
508 sha512 = "FBHEW6Jf5TB9MGBgUUA9XHkTbjXYfAUjY43ACMfmdMRHniyoMHjHjzD50OK8LGDWQwp4rWEsIq5kEqq7rvIM1g==";
509 };
510 };
511 "ajv-keywords-3.2.0" = {
505 version = "6.10.0";
506 src = fetchurl {
507 url = "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz";
508 sha512 = "nffhOpkymDECQyR0mnsUtoCE8RlX38G0rYP+wgLWFyZuUyuuojSSvi/+euOiQBIn63whYwYVIIH1TvE3tu4OEg==";
509 };
510 };
511 "ajv-keywords-3.4.0" = {
512 512 name = "ajv-keywords";
513 513 packageName = "ajv-keywords";
514 version = "3.2.0";
515 src = fetchurl {
516 url = "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.2.0.tgz";
517 sha1 = "e86b819c602cf8821ad637413698f1dec021847a";
514 version = "3.4.0";
515 src = fetchurl {
516 url = "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.4.0.tgz";
517 sha512 = "aUjdRFISbuFOl0EIZc+9e4FfZp0bDZgAdOOf30bJmw8VM9v84SHyVyxDfbWxpGYbdZD/9XoKxfHVNmxPkhwyGw==";
518 518 };
519 519 };
520 520 "align-text-0.1.4" = {
@@ -716,15 +716,6 b' let'
716 716 sha1 = "a894b75d4bc4f6cd679ef3244a9fd8f46ae2d428";
717 717 };
718 718 };
719 "arrify-1.0.1" = {
720 name = "arrify";
721 packageName = "arrify";
722 version = "1.0.1";
723 src = fetchurl {
724 url = "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz";
725 sha1 = "898508da2226f380df904728456849c1501a4b0d";
726 };
727 };
728 719 "asap-2.0.6" = {
729 720 name = "asap";
730 721 packageName = "asap";
@@ -752,13 +743,13 b' let'
752 743 sha512 = "p32cOF5q0Zqs9uBiONKYLm6BClCoBCM5O9JfeUSlnQLBTxYdTK+pW+nXflm8UkKd2UYlEbYz5qEi0JuZR9ckSw==";
753 744 };
754 745 };
755 "assert-1.4.1" = {
746 "assert-1.5.0" = {
756 747 name = "assert";
757 748 packageName = "assert";
758 version = "1.4.1";
759 src = fetchurl {
760 url = "https://registry.npmjs.org/assert/-/assert-1.4.1.tgz";
761 sha1 = "99912d591836b5a6f5b345c0f07eefc08fc65d91";
749 version = "1.5.0";
750 src = fetchurl {
751 url = "https://registry.npmjs.org/assert/-/assert-1.5.0.tgz";
752 sha512 = "EDsgawzwoun2CZkCgtxJbv392v4nbk9XDD06zI+kQYoBM/3RBWLlEyJARDOmhAAosBjWACEkKL6S+lIZtcAubA==";
762 753 };
763 754 };
764 755 "assert-plus-0.2.0" = {
@@ -815,22 +806,22 b' let'
815 806 sha1 = "b6bbe0b0674b9d719708ca38de8c237cb526c3d1";
816 807 };
817 808 };
818 "async-2.6.1" = {
809 "async-2.6.2" = {
819 810 name = "async";
820 811 packageName = "async";
821 version = "2.6.1";
822 src = fetchurl {
823 url = "https://registry.npmjs.org/async/-/async-2.6.1.tgz";
824 sha512 = "fNEiL2+AZt6AlAw/29Cr0UDe4sRAHCpEHh54WMz+Bb7QfNcFw4h3loofyJpLeQs4Yx7yuqu/2dLgM5hKOs6HlQ==";
825 };
826 };
827 "async-each-1.0.1" = {
812 version = "2.6.2";
813 src = fetchurl {
814 url = "https://registry.npmjs.org/async/-/async-2.6.2.tgz";
815 sha512 = "H1qVYh1MYhEEFLsP97cVKqCGo7KfCyTt6uEWqsTBr9SO84oK9Uwbyd/yCW+6rKJLHksBNUVWZDAjfS+Ccx0Bbg==";
816 };
817 };
818 "async-each-1.0.3" = {
828 819 name = "async-each";
829 820 packageName = "async-each";
830 version = "1.0.1";
831 src = fetchurl {
832 url = "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz";
833 sha1 = "19d386a1d9edc6e7c1c85d388aedbcc56d33602d";
821 version = "1.0.3";
822 src = fetchurl {
823 url = "https://registry.npmjs.org/async-each/-/async-each-1.0.3.tgz";
824 sha512 = "z/WhQ5FPySLdvREByI2vZiTWwCnF0moMJ1hK9YQwDTHKh6I7/uSckMetoRGb5UBZPC1z0jlw+n/XCgjeH7y1AQ==";
834 825 };
835 826 };
836 827 "asynckit-0.4.0" = {
@@ -1445,22 +1436,22 b' let'
1445 1436 sha512 = "vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==";
1446 1437 };
1447 1438 };
1448 "binary-extensions-1.12.0" = {
1439 "binary-extensions-1.13.1" = {
1449 1440 name = "binary-extensions";
1450 1441 packageName = "binary-extensions";
1451 version = "1.12.0";
1452 src = fetchurl {
1453 url = "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.12.0.tgz";
1454 sha512 = "DYWGk01lDcxeS/K9IHPGWfT8PsJmbXRtRd2Sx72Tnb8pcYZQFF1oSDb8hJtS1vhp212q1Rzi5dUf9+nq0o9UIg==";
1455 };
1456 };
1457 "bluebird-3.5.3" = {
1442 version = "1.13.1";
1443 src = fetchurl {
1444 url = "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.13.1.tgz";
1445 sha512 = "Un7MIEDdUC5gNpcGDV97op1Ywk748MpHcFTHoYs6qnj1Z3j7I53VG3nwZhKzoBZmbdRNnb6WRdFlwl7tSDuZGw==";
1446 };
1447 };
1448 "bluebird-3.5.4" = {
1458 1449 name = "bluebird";
1459 1450 packageName = "bluebird";
1460 version = "3.5.3";
1461 src = fetchurl {
1462 url = "https://registry.npmjs.org/bluebird/-/bluebird-3.5.3.tgz";
1463 sha512 = "/qKPUQlaW1OyR51WeCPBvRnAlnZFUJkCSG5HzGnuIqhgyJtF+T94lFnn33eiazjRm2LAHVy2guNnaq48X9SJuw==";
1451 version = "3.5.4";
1452 src = fetchurl {
1453 url = "https://registry.npmjs.org/bluebird/-/bluebird-3.5.4.tgz";
1454 sha512 = "FG+nFEZChJrbQ9tIccIfZJBz3J7mLrAhxakAbnrJWn8d7aKOC+LWifa0G+p4ZqKp4y13T7juYvdhq9NzKdsrjw==";
1464 1455 };
1465 1456 };
1466 1457 "bn.js-4.11.8" = {
@@ -1661,13 +1652,13 b' let'
1661 1652 sha1 = "9bb5304d2e0b56698b2c758b08a3eaa9daa58a39";
1662 1653 };
1663 1654 };
1664 "camelcase-5.0.0" = {
1655 "camelcase-5.3.1" = {
1665 1656 name = "camelcase";
1666 1657 packageName = "camelcase";
1667 version = "5.0.0";
1668 src = fetchurl {
1669 url = "https://registry.npmjs.org/camelcase/-/camelcase-5.0.0.tgz";
1670 sha512 = "faqwZqnWxbxn+F1d399ygeamQNy3lPp/H9H6rNrqYh4FSVCtcY+3cub1MxA8o9mDd55mM8Aghuu/kuyYA6VTsA==";
1658 version = "5.3.1";
1659 src = fetchurl {
1660 url = "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz";
1661 sha512 = "L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==";
1671 1662 };
1672 1663 };
1673 1664 "caniuse-api-1.6.1" = {
@@ -1679,22 +1670,22 b' let'
1679 1670 sha1 = "b534e7c734c4f81ec5fbe8aca2ad24354b962c6c";
1680 1671 };
1681 1672 };
1682 "caniuse-db-1.0.30000927" = {
1673 "caniuse-db-1.0.30000967" = {
1683 1674 name = "caniuse-db";
1684 1675 packageName = "caniuse-db";
1685 version = "1.0.30000927";
1686 src = fetchurl {
1687 url = "https://registry.npmjs.org/caniuse-db/-/caniuse-db-1.0.30000927.tgz";
1688 sha512 = "CX/QvLA8oh7kQ9cHCCzFm0UZW4KwSyQSRJ5A1XtH42HaMJQ0yh+9fEVWagMqv9I1vSCtaqA5Mb8k0uKfv7jhDw==";
1689 };
1690 };
1691 "caniuse-lite-1.0.30000927" = {
1676 version = "1.0.30000967";
1677 src = fetchurl {
1678 url = "https://registry.npmjs.org/caniuse-db/-/caniuse-db-1.0.30000967.tgz";
1679 sha512 = "70gk6cLSD5rItxnZ7WUxyCpM9LAjEb1tVzlENQfXQXZS/IiGnfAC6u32G5cZFlDBKjNPBIta/QSx5CZLZepxRA==";
1680 };
1681 };
1682 "caniuse-lite-1.0.30000967" = {
1692 1683 name = "caniuse-lite";
1693 1684 packageName = "caniuse-lite";
1694 version = "1.0.30000927";
1695 src = fetchurl {
1696 url = "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30000927.tgz";
1697 sha512 = "ogq4NbUWf1uG/j66k0AmiO3GjqJAlQyF8n4w8a954cbCyFKmYGvRtgz6qkq2fWuduTXHibX7GyYL5Pg58Aks2g==";
1685 version = "1.0.30000967";
1686 src = fetchurl {
1687 url = "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30000967.tgz";
1688 sha512 = "rUBIbap+VJfxTzrM4akJ00lkvVb5/n5v3EGXfWzSH5zT8aJmGzjA8HWhJ4U6kCpzxozUSnB+yvAYDRPY6mRpgQ==";
1698 1689 };
1699 1690 };
1700 1691 "caseless-0.12.0" = {
@@ -1742,13 +1733,13 b' let'
1742 1733 sha512 = "Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==";
1743 1734 };
1744 1735 };
1745 "chokidar-2.0.4" = {
1736 "chokidar-2.1.5" = {
1746 1737 name = "chokidar";
1747 1738 packageName = "chokidar";
1748 version = "2.0.4";
1749 src = fetchurl {
1750 url = "https://registry.npmjs.org/chokidar/-/chokidar-2.0.4.tgz";
1751 sha512 = "z9n7yt9rOvIJrMhvDtDictKrkFHeihkNl6uWMmZlmL6tJtX9Cs+87oK+teBx+JIgzvbX3yZHT3eF8vpbDxHJXQ==";
1739 version = "2.1.5";
1740 src = fetchurl {
1741 url = "https://registry.npmjs.org/chokidar/-/chokidar-2.1.5.tgz";
1742 sha512 = "i0TprVWp+Kj4WRPtInjexJ8Q+BqTE909VpH8xVhXrJkoc5QC8VO9TryGOqTr+2hljzc1sC62t22h5tZePodM/A==";
1752 1743 };
1753 1744 };
1754 1745 "chownr-1.1.1" = {
@@ -1976,13 +1967,13 b' let'
1976 1967 sha512 = "mmGt/1pZqYRjMxB1axhTo16/snVZ5krrKkcmMeVKxzECMMXoCgnvTPp10QgHfcbQZw8Dq2jMNG6je4JlWU0gWg==";
1977 1968 };
1978 1969 };
1979 "combined-stream-1.0.7" = {
1970 "combined-stream-1.0.8" = {
1980 1971 name = "combined-stream";
1981 1972 packageName = "combined-stream";
1982 version = "1.0.7";
1983 src = fetchurl {
1984 url = "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz";
1985 sha512 = "brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==";
1973 version = "1.0.8";
1974 src = fetchurl {
1975 url = "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz";
1976 sha512 = "FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==";
1986 1977 };
1987 1978 };
1988 1979 "commander-2.14.1" = {
@@ -2003,6 +1994,15 b' let'
2003 1994 sha512 = "wPMUt6FnH2yzG95SA6mzjQOEKUU3aLaDEmzs1ti+1E9h+CsrZghRlqEM/EJ4KscsQVG8uNN4uVreUeT8+drlgg==";
2004 1995 };
2005 1996 };
1997 "commander-2.19.0" = {
1998 name = "commander";
1999 packageName = "commander";
2000 version = "2.19.0";
2001 src = fetchurl {
2002 url = "https://registry.npmjs.org/commander/-/commander-2.19.0.tgz";
2003 sha512 = "6tvAOO+D6OENvRAh524Dh9jcfKTYDQAqvqezbCW82xj5X0pSrcpxtvRKHLG0yBY6SD7PSDrJaj+0AiOcKVd1Xg==";
2004 };
2005 };
2006 2006 "commondir-1.0.1" = {
2007 2007 name = "commondir";
2008 2008 packageName = "commondir";
@@ -2012,13 +2012,13 b' let'
2012 2012 sha1 = "ddd800da0c66127393cca5950ea968a3aaf1253b";
2013 2013 };
2014 2014 };
2015 "component-emitter-1.2.1" = {
2015 "component-emitter-1.3.0" = {
2016 2016 name = "component-emitter";
2017 2017 packageName = "component-emitter";
2018 version = "1.2.1";
2019 src = fetchurl {
2020 url = "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz";
2021 sha1 = "137918d6d78283f7df7a6b7c5a63e140e69425e6";
2018 version = "1.3.0";
2019 src = fetchurl {
2020 url = "https://registry.npmjs.org/component-emitter/-/component-emitter-1.3.0.tgz";
2021 sha512 = "Rd3se6QB+sO1TwqZjscQrurpEPIfO0/yYnSin6Q/rD3mOutHvUrCAhJub3r90uNb+SESBuE0QYoB90YdfatsRg==";
2022 2022 };
2023 2023 };
2024 2024 "concat-map-0.0.1" = {
@@ -2093,13 +2093,13 b' let'
2093 2093 sha512 = "Y+SQCF+0NoWQryez2zXn5J5knmr9z/9qSQt7fbL78u83rxmigOy8X5+BFn8CFSuX+nKT8gpYwJX68ekqtQt6ZA==";
2094 2094 };
2095 2095 };
2096 "core-js-2.6.1" = {
2096 "core-js-2.6.5" = {
2097 2097 name = "core-js";
2098 2098 packageName = "core-js";
2099 version = "2.6.1";
2100 src = fetchurl {
2101 url = "https://registry.npmjs.org/core-js/-/core-js-2.6.1.tgz";
2102 sha512 = "L72mmmEayPJBejKIWe2pYtGis5r0tQ5NaJekdhyXgeMQTpJoBsH0NL4ElY2LfSoV15xeQWKQ+XTTOZdyero5Xg==";
2099 version = "2.6.5";
2100 src = fetchurl {
2101 url = "https://registry.npmjs.org/core-js/-/core-js-2.6.5.tgz";
2102 sha512 = "klh/kDpwX8hryYL14M9w/xei6vrv6sE8gTHDG7/T/+SEovB/G4ejwcfE/CBzO6Edsu+OETZMZ3wcX/EjUkrl5A==";
2103 2103 };
2104 2104 };
2105 2105 "core-util-is-1.0.2" = {
@@ -2201,13 +2201,13 b' let'
2201 2201 sha512 = "xYL0AMZJ4gFzJQsHUKa5jiWWi2vH77WVNg7JYRyewwj6oPh4yb/y6Y9ZCw9dsj/9UauMhtuxR+ogQd//EdEVNA==";
2202 2202 };
2203 2203 };
2204 "css-what-2.1.2" = {
2204 "css-what-2.1.3" = {
2205 2205 name = "css-what";
2206 2206 packageName = "css-what";
2207 version = "2.1.2";
2208 src = fetchurl {
2209 url = "https://registry.npmjs.org/css-what/-/css-what-2.1.2.tgz";
2210 sha512 = "wan8dMWQ0GUeF7DGEPVjhHemVW/vy6xUYmFzRY8RYqgA0JtXC9rJmbScBjqSu6dg9q0lwPQy6ZAmJVr3PPTvqQ==";
2207 version = "2.1.3";
2208 src = fetchurl {
2209 url = "https://registry.npmjs.org/css-what/-/css-what-2.1.3.tgz";
2210 sha512 = "a+EPoD+uZiNfh+5fxw2nO9QwFa6nJe2Or35fGY6Ipw1R3R4AGz1d1TEZrCegvw2YTmZ0jXirGYlzxxpYSHwpEg==";
2211 2211 };
2212 2212 };
2213 2213 "cssesc-0.1.0" = {
@@ -2417,13 +2417,13 b' let'
2417 2417 sha512 = "kqag/Nl+f3GwyK25fhUMYj81BUOrZ9IuJsjIcDE5icNM9FJHAVm3VcUDxdLPoQtTuUylWm6ZIknYJwwaPxsUzg==";
2418 2418 };
2419 2419 };
2420 "dir-glob-2.0.0" = {
2420 "dir-glob-2.2.2" = {
2421 2421 name = "dir-glob";
2422 2422 packageName = "dir-glob";
2423 version = "2.0.0";
2424 src = fetchurl {
2425 url = "https://registry.npmjs.org/dir-glob/-/dir-glob-2.0.0.tgz";
2426 sha512 = "37qirFDz8cA5fimp9feo43fSuRo2gHwaIn6dXL8Ber1dGwUosDrGZeCCXq57WnIqE4aQ+u3eQZzsk1yOzhdwag==";
2423 version = "2.2.2";
2424 src = fetchurl {
2425 url = "https://registry.npmjs.org/dir-glob/-/dir-glob-2.2.2.tgz";
2426 sha512 = "f9LBi5QWzIW3I6e//uxZoLBlUt9kcp66qo0sSCxL6YZKc75R1c4MFCoe/LaZiBGmgujvQdxc5Bn3QhfyvK5Hsw==";
2427 2427 };
2428 2428 };
2429 2429 "dom-converter-0.2.0" = {
@@ -2435,13 +2435,13 b' let'
2435 2435 sha512 = "gd3ypIPfOMr9h5jIKq8E3sHOTCjeirnl0WK5ZdS1AW0Odt0b1PaWaHdJ4Qk4klv+YB9aJBS7mESXjFoDQPu6DA==";
2436 2436 };
2437 2437 };
2438 "dom-serializer-0.1.0" = {
2438 "dom-serializer-0.1.1" = {
2439 2439 name = "dom-serializer";
2440 2440 packageName = "dom-serializer";
2441 version = "0.1.0";
2442 src = fetchurl {
2443 url = "https://registry.npmjs.org/dom-serializer/-/dom-serializer-0.1.0.tgz";
2444 sha1 = "073c697546ce0780ce23be4a28e293e40bc30c82";
2441 version = "0.1.1";
2442 src = fetchurl {
2443 url = "https://registry.npmjs.org/dom-serializer/-/dom-serializer-0.1.1.tgz";
2444 sha512 = "l0IU0pPzLWSHBcieZbpOKgkIn3ts3vAh7ZuFyXNwJxJXk/c4Gwj9xaTJwIDVQCXawWD0qb3IzMGH5rglQaO0XA==";
2445 2445 };
2446 2446 };
2447 2447 "dom5-2.3.0" = {
@@ -2462,15 +2462,6 b' let'
2462 2462 sha512 = "jnjyiM6eRyZl2H+W8Q/zLMA481hzi0eszAaBUzIVnmYVDBbnLxVNnfu1HgEBvCbL+71FrxMl3E6lpKH7Ge3OXA==";
2463 2463 };
2464 2464 };
2465 "domelementtype-1.1.3" = {
2466 name = "domelementtype";
2467 packageName = "domelementtype";
2468 version = "1.1.3";
2469 src = fetchurl {
2470 url = "https://registry.npmjs.org/domelementtype/-/domelementtype-1.1.3.tgz";
2471 sha1 = "bd28773e2642881aec51544924299c5cd822185b";
2472 };
2473 };
2474 2465 "domelementtype-1.3.1" = {
2475 2466 name = "domelementtype";
2476 2467 packageName = "domelementtype";
@@ -2480,15 +2471,6 b' let'
2480 2471 sha512 = "BSKB+TSpMpFI/HOxCNr1O8aMOTZ8hT3pM3GQ0w/mWRmkhEDSFJkkyzz4XQsBV44BChwGkrDfMyjVD0eA2aFV3w==";
2481 2472 };
2482 2473 };
2483 "domhandler-2.1.0" = {
2484 name = "domhandler";
2485 packageName = "domhandler";
2486 version = "2.1.0";
2487 src = fetchurl {
2488 url = "https://registry.npmjs.org/domhandler/-/domhandler-2.1.0.tgz";
2489 sha1 = "d2646f5e57f6c3bab11cf6cb05d3c0acf7412594";
2490 };
2491 };
2492 2474 "domhandler-2.3.0" = {
2493 2475 name = "domhandler";
2494 2476 packageName = "domhandler";
@@ -2498,15 +2480,6 b' let'
2498 2480 sha1 = "2de59a0822d5027fabff6f032c2b25a2a8abe738";
2499 2481 };
2500 2482 };
2501 "domutils-1.1.6" = {
2502 name = "domutils";
2503 packageName = "domutils";
2504 version = "1.1.6";
2505 src = fetchurl {
2506 url = "https://registry.npmjs.org/domutils/-/domutils-1.1.6.tgz";
2507 sha1 = "bddc3de099b9a2efacc51c623f28f416ecc57485";
2508 };
2509 };
2510 2483 "domutils-1.5.1" = {
2511 2484 name = "domutils";
2512 2485 packageName = "domutils";
@@ -2516,13 +2489,22 b' let'
2516 2489 sha1 = "dcd8488a26f563d61079e48c9f7b7e32373682cf";
2517 2490 };
2518 2491 };
2519 "duplexify-3.6.1" = {
2492 "dropzone-5.5.1" = {
2493 name = "dropzone";
2494 packageName = "dropzone";
2495 version = "5.5.1";
2496 src = fetchurl {
2497 url = "https://registry.npmjs.org/dropzone/-/dropzone-5.5.1.tgz";
2498 sha512 = "3VduRWLxx9hbVr42QieQN25mx/I61/mRdUSuxAmDGdDqZIN8qtP7tcKMa3KfpJjuGjOJGYYUzzeq6eGDnkzesA==";
2499 };
2500 };
2501 "duplexify-3.7.1" = {
2520 2502 name = "duplexify";
2521 2503 packageName = "duplexify";
2522 version = "3.6.1";
2523 src = fetchurl {
2524 url = "https://registry.npmjs.org/duplexify/-/duplexify-3.6.1.tgz";
2525 sha512 = "vM58DwdnKmty+FSPzT14K9JXb90H+j5emaR4KYbr2KTIz00WHGbWOe5ghQTx233ZCLZtrGDALzKwcjEtSt35mA==";
2504 version = "3.7.1";
2505 src = fetchurl {
2506 url = "https://registry.npmjs.org/duplexify/-/duplexify-3.7.1.tgz";
2507 sha512 = "07z8uv2wMyS51kKhD1KsdXJg5WQ6t93RneqRxUHnskXVtlYYkLqM0gqStQZ3pj073g687jPCHrqNfCzawLYh5g==";
2526 2508 };
2527 2509 };
2528 2510 "ecc-jsbn-0.1.2" = {
@@ -2534,13 +2516,13 b' let'
2534 2516 sha1 = "3a83a904e54353287874c564b7549386849a98c9";
2535 2517 };
2536 2518 };
2537 "electron-to-chromium-1.3.98" = {
2519 "electron-to-chromium-1.3.133" = {
2538 2520 name = "electron-to-chromium";
2539 2521 packageName = "electron-to-chromium";
2540 version = "1.3.98";
2541 src = fetchurl {
2542 url = "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.98.tgz";
2543 sha512 = "WIZdNuvE3dFr6kkPgv4d/cfswNZD6XbeLBM8baOIQTsnbf4xWrVEaLvp7oNnbnMWWXDqq7Tbv+H5JfciLTJm4Q==";
2522 version = "1.3.133";
2523 src = fetchurl {
2524 url = "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.133.tgz";
2525 sha512 = "lyoC8aoqbbDqsprb6aPdt9n3DpOZZzdz/T4IZKsR0/dkZIxnJVUjjcpOSwA66jPRIOyDAamCTAUqweU05kKNSg==";
2544 2526 };
2545 2527 };
2546 2528 "elliptic-6.4.1" = {
@@ -2651,13 +2633,13 b' let'
2651 2633 sha1 = "1b61c0562190a8dff6ae3bb2cf0200ca130b86d4";
2652 2634 };
2653 2635 };
2654 "eslint-scope-4.0.0" = {
2636 "eslint-scope-4.0.3" = {
2655 2637 name = "eslint-scope";
2656 2638 packageName = "eslint-scope";
2657 version = "4.0.0";
2658 src = fetchurl {
2659 url = "https://registry.npmjs.org/eslint-scope/-/eslint-scope-4.0.0.tgz";
2660 sha512 = "1G6UTDi7Jc1ELFwnR58HV4fK9OQK4S6N985f166xqXxpjU6plxFISJa2Ba9KCQuFa8RCnj/lSFJbHo7UFDBnUA==";
2639 version = "4.0.3";
2640 src = fetchurl {
2641 url = "https://registry.npmjs.org/eslint-scope/-/eslint-scope-4.0.3.tgz";
2642 sha512 = "p7VutNr1O/QrxysMo3E45FjYDTeXBy0iTltPFNSqKAIfjDSXC+4dj+qfyuD8bfAXrW/y6lW3O76VaYNPKfpKrg==";
2661 2643 };
2662 2644 };
2663 2645 "espree-3.5.4" = {
@@ -2732,13 +2714,13 b' let'
2732 2714 sha1 = "8f61b75cde012b2e9eb284d4545583b5643b61ab";
2733 2715 };
2734 2716 };
2735 "events-1.1.1" = {
2717 "events-3.0.0" = {
2736 2718 name = "events";
2737 2719 packageName = "events";
2738 version = "1.1.1";
2739 src = fetchurl {
2740 url = "https://registry.npmjs.org/events/-/events-1.1.1.tgz";
2741 sha1 = "9ebdb7635ad099c70dcc4c2a1f5004288e8bd924";
2720 version = "3.0.0";
2721 src = fetchurl {
2722 url = "https://registry.npmjs.org/events/-/events-3.0.0.tgz";
2723 sha512 = "Dc381HFWJzEOhQ+d8pkNon++bk9h6cdAoAj4iE6Q4y6xgTzySWXlKn05/TVNpjnfRqi/X0EpJEJohPjNI3zpVA==";
2742 2724 };
2743 2725 };
2744 2726 "evp_bytestokey-1.0.3" = {
@@ -2948,13 +2930,13 b' let'
2948 2930 sha1 = "9326b1488c22d1a6088650a86901b2d9a90a2cbc";
2949 2931 };
2950 2932 };
2951 "fined-1.1.1" = {
2933 "fined-1.2.0" = {
2952 2934 name = "fined";
2953 2935 packageName = "fined";
2954 version = "1.1.1";
2955 src = fetchurl {
2956 url = "https://registry.npmjs.org/fined/-/fined-1.1.1.tgz";
2957 sha512 = "jQp949ZmEbiYHk3gkbdtpJ0G1+kgtLQBNdP5edFP7Fh+WAYceLQz6yO1SBj72Xkg8GVyTB3bBzAYrHJVh5Xd5g==";
2936 version = "1.2.0";
2937 src = fetchurl {
2938 url = "https://registry.npmjs.org/fined/-/fined-1.2.0.tgz";
2939 sha512 = "ZYDqPLGxDkDhDZBjZBb+oD1+j0rA4E0pXY50eplAAOPg2N/gUBSSk5IM1/QhPfyVo19lJ+CvXpqfvk+b2p/8Ng==";
2958 2940 };
2959 2941 };
2960 2942 "flagged-respawn-1.0.1" = {
@@ -2975,13 +2957,13 b' let'
2975 2957 sha1 = "dae46a9d78fbe25292258cc1e780a41d95c03782";
2976 2958 };
2977 2959 };
2978 "flush-write-stream-1.0.3" = {
2960 "flush-write-stream-1.1.1" = {
2979 2961 name = "flush-write-stream";
2980 2962 packageName = "flush-write-stream";
2981 version = "1.0.3";
2982 src = fetchurl {
2983 url = "https://registry.npmjs.org/flush-write-stream/-/flush-write-stream-1.0.3.tgz";
2984 sha512 = "calZMC10u0FMUqoiunI2AiGIIUtUIvifNwkHhNupZH4cbNnW1Itkoh/Nf5HFYmDrwWPjrUxpkZT0KhuCq0jmGw==";
2963 version = "1.1.1";
2964 src = fetchurl {
2965 url = "https://registry.npmjs.org/flush-write-stream/-/flush-write-stream-1.1.1.tgz";
2966 sha512 = "3Z4XhFZ3992uIq0XOqb9AreonueSYphE6oYbpt5+3u06JWklbsPkNv3ZKkP9Bz/r+1MWCaMoSQ28P85+1Yc77w==";
2985 2967 };
2986 2968 };
2987 2969 "for-in-1.0.2" = {
@@ -3056,13 +3038,13 b' let'
3056 3038 sha1 = "1504ad2523158caa40db4a2787cb01411994ea4f";
3057 3039 };
3058 3040 };
3059 "fsevents-1.2.4" = {
3041 "fsevents-1.2.9" = {
3060 3042 name = "fsevents";
3061 3043 packageName = "fsevents";
3062 version = "1.2.4";
3063 src = fetchurl {
3064 url = "https://registry.npmjs.org/fsevents/-/fsevents-1.2.4.tgz";
3065 sha512 = "z8H8/diyk76B7q5wg+Ud0+CqzcAF3mBBI/bA5ne5zrRUUIvNkJY//D3BqyH571KuAC4Nr7Rw7CjWX4r0y9DvNg==";
3044 version = "1.2.9";
3045 src = fetchurl {
3046 url = "https://registry.npmjs.org/fsevents/-/fsevents-1.2.9.tgz";
3047 sha512 = "oeyj2H3EjjonWcFjD5NvZNE9Rqe4UW+nQBU2HNeKw0koVLEFIhtyETyAakeAM3de7Z/SW5kcA+fZUait9EApnw==";
3066 3048 };
3067 3049 };
3068 3050 "function-bind-1.1.1" = {
@@ -3146,13 +3128,13 b' let'
3146 3128 sha1 = "4a973f635b9190f715d10987d5c00fd2815ebe3d";
3147 3129 };
3148 3130 };
3149 "glob-7.1.3" = {
3131 "glob-7.1.4" = {
3150 3132 name = "glob";
3151 3133 packageName = "glob";
3152 version = "7.1.3";
3153 src = fetchurl {
3154 url = "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz";
3155 sha512 = "vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==";
3134 version = "7.1.4";
3135 src = fetchurl {
3136 url = "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz";
3137 sha512 = "hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==";
3156 3138 };
3157 3139 };
3158 3140 "glob-parent-3.1.0" = {
@@ -3524,13 +3506,13 b' let'
3524 3506 sha1 = "e36c3f2d2cae7d746a857e38d18d5f32a7882db8";
3525 3507 };
3526 3508 };
3527 "homedir-polyfill-1.0.1" = {
3509 "homedir-polyfill-1.0.3" = {
3528 3510 name = "homedir-polyfill";
3529 3511 packageName = "homedir-polyfill";
3530 version = "1.0.1";
3531 src = fetchurl {
3532 url = "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz";
3533 sha1 = "4c2bbc8a758998feebf5ed68580f76d46768b4bc";
3512 version = "1.0.3";
3513 src = fetchurl {
3514 url = "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.3.tgz";
3515 sha512 = "eSmmWE5bZTK2Nou4g0AI3zZ9rswp7GRKoKXS1BLUkvPviOqs4YTN1djQIqrXy9k5gEtdLPy86JjRwsNM9tnDcA==";
3534 3516 };
3535 3517 };
3536 3518 "hooker-0.2.3" = {
@@ -3587,15 +3569,6 b' let'
3587 3569 sha1 = "b01abbd723acaaa7b37b6af4492ebda03d9dd37b";
3588 3570 };
3589 3571 };
3590 "htmlparser2-3.3.0" = {
3591 name = "htmlparser2";
3592 packageName = "htmlparser2";
3593 version = "3.3.0";
3594 src = fetchurl {
3595 url = "https://registry.npmjs.org/htmlparser2/-/htmlparser2-3.3.0.tgz";
3596 sha1 = "cc70d05a59f6542e43f0e685c982e14c924a9efe";
3597 };
3598 };
3599 3572 "htmlparser2-3.8.3" = {
3600 3573 name = "htmlparser2";
3601 3574 packageName = "htmlparser2";
@@ -3650,13 +3623,13 b' let'
3650 3623 sha1 = "83f0a0ec378bf3246178b6c2ad9136f135b1c962";
3651 3624 };
3652 3625 };
3653 "ieee754-1.1.12" = {
3626 "ieee754-1.1.13" = {
3654 3627 name = "ieee754";
3655 3628 packageName = "ieee754";
3656 version = "1.1.12";
3657 src = fetchurl {
3658 url = "https://registry.npmjs.org/ieee754/-/ieee754-1.1.12.tgz";
3659 sha512 = "GguP+DRY+pJ3soyIiGPTvdiVXjZ+DbXOxGpXn3eMvNW4x4irjqXm4wHKscC+TfxSJ0yw/S1F24tqdMNsMZTiLA==";
3629 version = "1.1.13";
3630 src = fetchurl {
3631 url = "https://registry.npmjs.org/ieee754/-/ieee754-1.1.13.tgz";
3632 sha512 = "4vf7I2LYV/HaWerSo3XmlMkp5eZ83i+/CDluXi/IGTs/O1sejBNhTtnxzmRZfvOUqj7lZjqHkeTvpgSFDlWZTg==";
3660 3633 };
3661 3634 };
3662 3635 "iferr-0.1.5" = {
@@ -3974,13 +3947,13 b' let'
3974 3947 sha1 = "7ba5ae24217804ac70707b96922567486cc3e84a";
3975 3948 };
3976 3949 };
3977 "is-glob-4.0.0" = {
3950 "is-glob-4.0.1" = {
3978 3951 name = "is-glob";
3979 3952 packageName = "is-glob";
3980 version = "4.0.0";
3981 src = fetchurl {
3982 url = "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz";
3983 sha1 = "9521c76845cc2610a85203ddf080a958c2ffabc0";
3953 version = "4.0.1";
3954 src = fetchurl {
3955 url = "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz";
3956 sha512 = "5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==";
3984 3957 };
3985 3958 };
3986 3959 "is-number-3.0.0" = {
@@ -4145,13 +4118,13 b' let'
4145 4118 sha1 = "dd8b74278b27102d29df63eae28308a8cfa1b583";
4146 4119 };
4147 4120 };
4148 "js-base64-2.5.0" = {
4121 "js-base64-2.5.1" = {
4149 4122 name = "js-base64";
4150 4123 packageName = "js-base64";
4151 version = "2.5.0";
4152 src = fetchurl {
4153 url = "https://registry.npmjs.org/js-base64/-/js-base64-2.5.0.tgz";
4154 sha512 = "wlEBIZ5LP8usDylWbDNhKPEFVFdI5hCHpnVoT/Ysvoi/PRhJENm/Rlh9TvjYB38HFfKZN7OzEbRjmjvLkFw11g==";
4124 version = "2.5.1";
4125 src = fetchurl {
4126 url = "https://registry.npmjs.org/js-base64/-/js-base64-2.5.1.tgz";
4127 sha512 = "M7kLczedRMYX4L8Mdh4MzyAMM9O5osx+4FcOQuTvr3A9F2D9S5JXheN0ewNbrvK2UatkTRhL5ejGmGSjNMiZuw==";
4155 4128 };
4156 4129 };
4157 4130 "js-tokens-3.0.2" = {
@@ -4208,6 +4181,15 b' let'
4208 4181 sha1 = "46c3fec8c1892b12b0833db9bc7622176dbab34b";
4209 4182 };
4210 4183 };
4184 "jshint-2.10.2" = {
4185 name = "jshint";
4186 packageName = "jshint";
4187 version = "2.10.2";
4188 src = fetchurl {
4189 url = "https://registry.npmjs.org/jshint/-/jshint-2.10.2.tgz";
4190 sha512 = "e7KZgCSXMJxznE/4WULzybCMNXNAd/bf5TSrvVEq78Q/K8ZwFpmBqQeDtNiHc3l49nV4E/+YeHU/JZjSUIrLAA==";
4191 };
4192 };
4211 4193 "jshint-2.9.7" = {
4212 4194 name = "jshint";
4213 4195 packageName = "jshint";
@@ -4370,13 +4352,13 b' let'
4370 4352 sha1 = "2009291bb31cea861bbf10a7c15a28caf75c31ec";
4371 4353 };
4372 4354 };
4373 "loader-runner-2.3.1" = {
4355 "loader-runner-2.4.0" = {
4374 4356 name = "loader-runner";
4375 4357 packageName = "loader-runner";
4376 version = "2.3.1";
4377 src = fetchurl {
4378 url = "https://registry.npmjs.org/loader-runner/-/loader-runner-2.3.1.tgz";
4379 sha512 = "By6ZFY7ETWOc9RFaAIb23IjJVcM4dvJC/N57nmdz9RSkMXvAXGI7SyVlAw3v8vjtDRlqThgVDVmTnr9fqMlxkw==";
4358 version = "2.4.0";
4359 src = fetchurl {
4360 url = "https://registry.npmjs.org/loader-runner/-/loader-runner-2.4.0.tgz";
4361 sha512 = "Jsmr89RcXGIwivFY21FcRrisYZfvLMTWx5kOLc+JTxtpBOG6xML0vzbc6SEQG2FO9/4Fc3wW4LVcB5DmGflaRw==";
4380 4362 };
4381 4363 };
4382 4364 "loader-utils-0.2.17" = {
@@ -4460,15 +4442,6 b' let'
4460 4442 sha1 = "b28aa6288a2b9fc651035c7711f65ab6190331a6";
4461 4443 };
4462 4444 };
4463 "lodash.debounce-4.0.8" = {
4464 name = "lodash.debounce";
4465 packageName = "lodash.debounce";
4466 version = "4.0.8";
4467 src = fetchurl {
4468 url = "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz";
4469 sha1 = "82d79bff30a67c4005ffd5e2515300ad9ca4d7af";
4470 };
4471 };
4472 4445 "lodash.isplainobject-4.0.6" = {
4473 4446 name = "lodash.isplainobject";
4474 4447 packageName = "lodash.isplainobject";
@@ -4613,13 +4586,13 b' let'
4613 4586 sha512 = "xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg==";
4614 4587 };
4615 4588 };
4616 "mem-4.0.0" = {
4589 "mem-4.3.0" = {
4617 4590 name = "mem";
4618 4591 packageName = "mem";
4619 version = "4.0.0";
4620 src = fetchurl {
4621 url = "https://registry.npmjs.org/mem/-/mem-4.0.0.tgz";
4622 sha512 = "WQxG/5xYc3tMbYLXoXPm81ET2WDULiU5FxbuIoNbJqLOOI8zehXFdZuiUEgfdrU2mVB1pxBZUGlYORSrpuJreA==";
4592 version = "4.3.0";
4593 src = fetchurl {
4594 url = "https://registry.npmjs.org/mem/-/mem-4.3.0.tgz";
4595 sha512 = "qX2bG48pTqYRVmDB37rn/6PT7LcR8T7oAX3bf99u1Tt1nzxYfxkgqDwUwolPlXweM0XzBOBFzSx4kfp7KP1s/w==";
4623 4596 };
4624 4597 };
4625 4598 "memory-fs-0.4.1" = {
@@ -4658,31 +4631,31 b' let'
4658 4631 sha512 = "x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==";
4659 4632 };
4660 4633 };
4661 "mime-db-1.37.0" = {
4634 "mime-db-1.40.0" = {
4662 4635 name = "mime-db";
4663 4636 packageName = "mime-db";
4664 version = "1.37.0";
4665 src = fetchurl {
4666 url = "https://registry.npmjs.org/mime-db/-/mime-db-1.37.0.tgz";
4667 sha512 = "R3C4db6bgQhlIhPU48fUtdVmKnflq+hRdad7IyKhtFj06VPNVdk2RhiYL3UjQIlso8L+YxAtFkobT0VK+S/ybg==";
4668 };
4669 };
4670 "mime-types-2.1.21" = {
4637 version = "1.40.0";
4638 src = fetchurl {
4639 url = "https://registry.npmjs.org/mime-db/-/mime-db-1.40.0.tgz";
4640 sha512 = "jYdeOMPy9vnxEqFRRo6ZvTZ8d9oPb+k18PKoYNYUe2stVEBPPwsln/qWzdbmaIvnhZ9v2P+CuecK+fpUfsV2mA==";
4641 };
4642 };
4643 "mime-types-2.1.24" = {
4671 4644 name = "mime-types";
4672 4645 packageName = "mime-types";
4673 version = "2.1.21";
4674 src = fetchurl {
4675 url = "https://registry.npmjs.org/mime-types/-/mime-types-2.1.21.tgz";
4676 sha512 = "3iL6DbwpyLzjR3xHSFNFeb9Nz/M8WDkX33t1GFQnFOllWk8pOrh/LSrB5OXlnlW5P9LH73X6loW/eogc+F5lJg==";
4677 };
4678 };
4679 "mimic-fn-1.2.0" = {
4646 version = "2.1.24";
4647 src = fetchurl {
4648 url = "https://registry.npmjs.org/mime-types/-/mime-types-2.1.24.tgz";
4649 sha512 = "WaFHS3MCl5fapm3oLxU4eYDw77IQM2ACcxQ9RIxfaC3ooc6PFuBMGZZsYpvoXS5D5QTWPieo1jjLdAm3TBP3cQ==";
4650 };
4651 };
4652 "mimic-fn-2.1.0" = {
4680 4653 name = "mimic-fn";
4681 4654 packageName = "mimic-fn";
4682 version = "1.2.0";
4683 src = fetchurl {
4684 url = "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz";
4685 sha512 = "jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==";
4655 version = "2.1.0";
4656 src = fetchurl {
4657 url = "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz";
4658 sha512 = "OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==";
4686 4659 };
4687 4660 };
4688 4661 "minimalistic-assert-1.0.1" = {
@@ -4775,22 +4748,22 b' let'
4775 4748 sha1 = "30057438eac6cf7f8c4767f38648d6697d75c903";
4776 4749 };
4777 4750 };
4778 "moment-2.23.0" = {
4751 "moment-2.24.0" = {
4779 4752 name = "moment";
4780 4753 packageName = "moment";
4781 version = "2.23.0";
4782 src = fetchurl {
4783 url = "https://registry.npmjs.org/moment/-/moment-2.23.0.tgz";
4784 sha512 = "3IE39bHVqFbWWaPOMHZF98Q9c3LDKGTmypMiTM2QygGXXElkFWIH7GxfmlwmY2vwa+wmNsoYZmG2iusf1ZjJoA==";
4785 };
4786 };
4787 "mousetrap-1.6.2" = {
4754 version = "2.24.0";
4755 src = fetchurl {
4756 url = "https://registry.npmjs.org/moment/-/moment-2.24.0.tgz";
4757 sha512 = "bV7f+6l2QigeBBZSM/6yTNq4P2fNpSWj/0e7jQcy87A8e7o2nAfP/34/2ky5Vw4B9S446EtIhodAzkFCcR4dQg==";
4758 };
4759 };
4760 "mousetrap-1.6.3" = {
4788 4761 name = "mousetrap";
4789 4762 packageName = "mousetrap";
4790 version = "1.6.2";
4791 src = fetchurl {
4792 url = "https://registry.npmjs.org/mousetrap/-/mousetrap-1.6.2.tgz";
4793 sha512 = "jDjhi7wlHwdO6q6DS7YRmSHcuI+RVxadBkLt3KHrhd3C2b+w5pKefg3oj5beTcHZyVFA9Aksf+yEE1y5jxUjVA==";
4763 version = "1.6.3";
4764 src = fetchurl {
4765 url = "https://registry.npmjs.org/mousetrap/-/mousetrap-1.6.3.tgz";
4766 sha512 = "bd+nzwhhs9ifsUrC2tWaSgm24/oo2c83zaRyZQF06hYA6sANfsXHtnZ19AbbbDXCDzeH5nZBSQ4NvCjgD62tJA==";
4794 4767 };
4795 4768 };
4796 4769 "move-concurrently-1.0.1" = {
@@ -4811,13 +4784,13 b' let'
4811 4784 sha1 = "5608aeadfc00be6c2901df5f9861788de0d597c8";
4812 4785 };
4813 4786 };
4814 "nan-2.12.1" = {
4787 "nan-2.13.2" = {
4815 4788 name = "nan";
4816 4789 packageName = "nan";
4817 version = "2.12.1";
4818 src = fetchurl {
4819 url = "https://registry.npmjs.org/nan/-/nan-2.12.1.tgz";
4820 sha512 = "JY7V6lRkStKcKTvHO5NVSQRv+RV+FIL5pvDoLiAtSL9pKlC5x9PKQcZDsq7m4FO4d57mkhC6Z+QhAh3Jdk5JFw==";
4790 version = "2.13.2";
4791 src = fetchurl {
4792 url = "https://registry.npmjs.org/nan/-/nan-2.13.2.tgz";
4793 sha512 = "TghvYc72wlMGMVMluVo9WRJc0mB8KxxF/gZ4YYFy7V2ZQX9l7rgbPg7vjS9mt6U5HXODVFVI2bOduCzwOMv/lw==";
4821 4794 };
4822 4795 };
4823 4796 "nanomatch-1.2.13" = {
@@ -4829,13 +4802,13 b' let'
4829 4802 sha512 = "fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==";
4830 4803 };
4831 4804 };
4832 "neo-async-2.6.0" = {
4805 "neo-async-2.6.1" = {
4833 4806 name = "neo-async";
4834 4807 packageName = "neo-async";
4835 version = "2.6.0";
4836 src = fetchurl {
4837 url = "https://registry.npmjs.org/neo-async/-/neo-async-2.6.0.tgz";
4838 sha512 = "MFh0d/Wa7vkKO3Y3LlacqAEeHK0mckVqzDieUKTT+KGxi+zIpeVsFxymkIiRpbpDziHc290Xr9A1O4Om7otoRA==";
4808 version = "2.6.1";
4809 src = fetchurl {
4810 url = "https://registry.npmjs.org/neo-async/-/neo-async-2.6.1.tgz";
4811 sha512 = "iyam8fBuCUpWeKPGpaNMetEocMt364qkCsfL9JuhjXX6dRnguRVOfk2GZaDpPjcOKiiXCPINZC1GczQ7iTq3Zw==";
4839 4812 };
4840 4813 };
4841 4814 "nice-try-1.0.5" = {
@@ -4856,13 +4829,13 b' let'
4856 4829 sha512 = "rmTZ9kz+f3rCvK2TD1Ue/oZlns7OGoIWP4fc3llxxRXlOkHKoWPPWJOfFYpITabSow43QJbRIoHQXtt10VldyQ==";
4857 4830 };
4858 4831 };
4859 "node-libs-browser-2.1.0" = {
4832 "node-libs-browser-2.2.0" = {
4860 4833 name = "node-libs-browser";
4861 4834 packageName = "node-libs-browser";
4862 version = "2.1.0";
4863 src = fetchurl {
4864 url = "https://registry.npmjs.org/node-libs-browser/-/node-libs-browser-2.1.0.tgz";
4865 sha512 = "5AzFzdoIMb89hBGMZglEegffzgRg+ZFoUmisQ8HI4j1KDdpx13J0taNp2y9xPbur6W61gepGDDotGBVQ7mfUCg==";
4835 version = "2.2.0";
4836 src = fetchurl {
4837 url = "https://registry.npmjs.org/node-libs-browser/-/node-libs-browser-2.2.0.tgz";
4838 sha512 = "5MQunG/oyOaBdttrL40dA7bUfPORLRWMUJLQtMg7nluxUvk5XwnLdL9twQHFAjRx/y7mIMkLKT9++qPbbk6BZA==";
4866 4839 };
4867 4840 };
4868 4841 "nopt-1.0.10" = {
@@ -4910,6 +4883,15 b' let'
4910 4883 sha1 = "1ab28b556e198363a8c1a6f7e6fa20137fe6aed9";
4911 4884 };
4912 4885 };
4886 "normalize-path-3.0.0" = {
4887 name = "normalize-path";
4888 packageName = "normalize-path";
4889 version = "3.0.0";
4890 src = fetchurl {
4891 url = "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz";
4892 sha512 = "6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==";
4893 };
4894 };
4913 4895 "normalize-range-0.1.2" = {
4914 4896 name = "normalize-range";
4915 4897 packageName = "normalize-range";
@@ -4991,13 +4973,13 b' let'
4991 4973 sha1 = "7e7d858b781bd7c991a41ba975ed3812754e998c";
4992 4974 };
4993 4975 };
4994 "object-keys-1.0.12" = {
4976 "object-keys-1.1.1" = {
4995 4977 name = "object-keys";
4996 4978 packageName = "object-keys";
4997 version = "1.0.12";
4998 src = fetchurl {
4999 url = "https://registry.npmjs.org/object-keys/-/object-keys-1.0.12.tgz";
5000 sha512 = "FTMyFUm2wBcGHnH2eXmz7tC6IwlqQZ6mVZ+6dm6vZ4IQIHjs6FdNsQBuKGPuUUUY6NfJw2PshC08Tn6LzLDOag==";
4979 version = "1.1.1";
4980 src = fetchurl {
4981 url = "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz";
4982 sha512 = "NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==";
5001 4983 };
5002 4984 };
5003 4985 "object-visit-1.0.1" = {
@@ -5117,13 +5099,13 b' let'
5117 5099 sha1 = "3fbcfb15b899a44123b34b6dcc18b724336a2cae";
5118 5100 };
5119 5101 };
5120 "p-is-promise-1.1.0" = {
5102 "p-is-promise-2.1.0" = {
5121 5103 name = "p-is-promise";
5122 5104 packageName = "p-is-promise";
5123 version = "1.1.0";
5124 src = fetchurl {
5125 url = "https://registry.npmjs.org/p-is-promise/-/p-is-promise-1.1.0.tgz";
5126 sha1 = "9c9456989e9f6588017b0434d56097675c3da05e";
5105 version = "2.1.0";
5106 src = fetchurl {
5107 url = "https://registry.npmjs.org/p-is-promise/-/p-is-promise-2.1.0.tgz";
5108 sha512 = "Y3W0wlRPK8ZMRbNq97l4M5otioeA5lm1z7bkNkxCka8HSPjR0xRWmpCmc9utiaLP9Jb1eD8BgeIxTW4AIF45Pg==";
5127 5109 };
5128 5110 };
5129 5111 "p-limit-1.3.0" = {
@@ -5135,13 +5117,13 b' let'
5135 5117 sha512 = "vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==";
5136 5118 };
5137 5119 };
5138 "p-limit-2.1.0" = {
5120 "p-limit-2.2.0" = {
5139 5121 name = "p-limit";
5140 5122 packageName = "p-limit";
5141 version = "2.1.0";
5142 src = fetchurl {
5143 url = "https://registry.npmjs.org/p-limit/-/p-limit-2.1.0.tgz";
5144 sha512 = "NhURkNcrVB+8hNfLuysU8enY5xn2KXphsHBaC2YmRNTZRc7RWusw6apSpdEj3jo4CMb6W9nrF6tTnsJsJeyu6g==";
5123 version = "2.2.0";
5124 src = fetchurl {
5125 url = "https://registry.npmjs.org/p-limit/-/p-limit-2.2.0.tgz";
5126 sha512 = "pZbTJpoUsCzV48Mc9Nh51VbwO0X9cuPFE8gYwx9BTCt9SF8/b7Zljd2fVgOxhIF/HDTKgpVzs+GPhyKfjLLFRQ==";
5145 5127 };
5146 5128 };
5147 5129 "p-locate-2.0.0" = {
@@ -5171,22 +5153,22 b' let'
5171 5153 sha1 = "cbc79cdbaf8fd4228e13f621f2b1a237c1b207b3";
5172 5154 };
5173 5155 };
5174 "p-try-2.0.0" = {
5156 "p-try-2.2.0" = {
5175 5157 name = "p-try";
5176 5158 packageName = "p-try";
5177 version = "2.0.0";
5178 src = fetchurl {
5179 url = "https://registry.npmjs.org/p-try/-/p-try-2.0.0.tgz";
5180 sha512 = "hMp0onDKIajHfIkdRk3P4CdCmErkYAxxDtP3Wx/4nZ3aGlau2VKh3mZpcuFkH27WQkL/3WBCPOktzA9ZOAnMQQ==";
5181 };
5182 };
5183 "pako-1.0.7" = {
5159 version = "2.2.0";
5160 src = fetchurl {
5161 url = "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz";
5162 sha512 = "R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==";
5163 };
5164 };
5165 "pako-1.0.10" = {
5184 5166 name = "pako";
5185 5167 packageName = "pako";
5186 version = "1.0.7";
5187 src = fetchurl {
5188 url = "https://registry.npmjs.org/pako/-/pako-1.0.7.tgz";
5189 sha512 = "3HNK5tW4x8o5mO8RuHZp3Ydw9icZXx0RANAOMzlMzx7LVXhMJ4mo3MOBpzyd7r/+RUu8BmndP47LXT+vzjtWcQ==";
5168 version = "1.0.10";
5169 src = fetchurl {
5170 url = "https://registry.npmjs.org/pako/-/pako-1.0.10.tgz";
5171 sha512 = "0DTvPVU3ed8+HNXOu5Bs+o//Mbdj9VNQMUOe9oKCwh8l0GNwpTDMKCWbRjgtD291AWnkAgkqA/LOnQS8AmS1tw==";
5190 5172 };
5191 5173 };
5192 5174 "parallel-transform-1.1.0" = {
@@ -5207,13 +5189,13 b' let'
5207 5189 sha1 = "df94fd8cf6531ecf75e6bef9a0858fbc72be2247";
5208 5190 };
5209 5191 };
5210 "parse-asn1-5.1.1" = {
5192 "parse-asn1-5.1.4" = {
5211 5193 name = "parse-asn1";
5212 5194 packageName = "parse-asn1";
5213 version = "5.1.1";
5214 src = fetchurl {
5215 url = "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.1.tgz";
5216 sha512 = "KPx7flKXg775zZpnp9SxJlz00gTd4BmJ2yJufSc44gMCRrRQ7NSzAcSJQfifuOLgW6bEi+ftrALtsgALeB2Adw==";
5195 version = "5.1.4";
5196 src = fetchurl {
5197 url = "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.4.tgz";
5198 sha512 = "Qs5duJcuvNExRfFZ99HDD3z4mAi3r9Wl/FOjEOijlxwCZs7E7mW2vjTpgQ4J8LpTF8x5v+1Vn5UQFejmWT11aw==";
5217 5199 };
5218 5200 };
5219 5201 "parse-filepath-1.0.2" = {
@@ -5927,13 +5909,13 b' let'
5927 5909 sha1 = "9ec61f79049875707d69414596fd907a4d711e73";
5928 5910 };
5929 5911 };
5930 "randombytes-2.0.6" = {
5912 "randombytes-2.1.0" = {
5931 5913 name = "randombytes";
5932 5914 packageName = "randombytes";
5933 version = "2.0.6";
5934 src = fetchurl {
5935 url = "https://registry.npmjs.org/randombytes/-/randombytes-2.0.6.tgz";
5936 sha512 = "CIQ5OFxf4Jou6uOKe9t1AOgqpeU5fd70A8NPdHSGeYXqXsPe6peOwI0cUl88RWZ6sP1vPMV3avd/R6cZ5/sP1A==";
5915 version = "2.1.0";
5916 src = fetchurl {
5917 url = "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz";
5918 sha512 = "vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==";
5937 5919 };
5938 5920 };
5939 5921 "randomfill-1.0.4" = {
@@ -5954,15 +5936,6 b' let'
5954 5936 sha512 = "guh4ZNAf96f+CDwfnPbFeFiO5YcfPllUmZrgcoOmx6iqZPq+DcKbnyjPuBxEAtQ3tqqd++qChsQfQB+VBzFT0Q==";
5955 5937 };
5956 5938 };
5957 "readable-stream-1.0.34" = {
5958 name = "readable-stream";
5959 packageName = "readable-stream";
5960 version = "1.0.34";
5961 src = fetchurl {
5962 url = "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz";
5963 sha1 = "125820e34bc842d2f2aaafafe4c2916ee32c157c";
5964 };
5965 };
5966 5939 "readable-stream-1.1.14" = {
5967 5940 name = "readable-stream";
5968 5941 packageName = "readable-stream";
@@ -6116,13 +6089,13 b' let'
6116 6089 sha1 = "c24bce2a283adad5bc3f58e0d48249b92379d8ef";
6117 6090 };
6118 6091 };
6119 "renderkid-2.0.2" = {
6092 "renderkid-2.0.3" = {
6120 6093 name = "renderkid";
6121 6094 packageName = "renderkid";
6122 version = "2.0.2";
6123 src = fetchurl {
6124 url = "https://registry.npmjs.org/renderkid/-/renderkid-2.0.2.tgz";
6125 sha512 = "FsygIxevi1jSiPY9h7vZmBFUbAOcbYm9UwyiLNdVsLRs/5We9Ob5NMPbGYUTWiLq5L+ezlVdE0A8bbME5CWTpg==";
6095 version = "2.0.3";
6096 src = fetchurl {
6097 url = "https://registry.npmjs.org/renderkid/-/renderkid-2.0.3.tgz";
6098 sha512 = "z8CLQp7EZBPCwCnncgf9C4XAi3WR0dv+uWu/PjIyhhAb5d6IJ/QZqlHFprHeKT+59//V6BNUsLbvN8+2LarxGA==";
6126 6099 };
6127 6100 };
6128 6101 "repeat-element-1.1.3" = {
@@ -6179,13 +6152,13 b' let'
6179 6152 sha1 = "97f717b69d48784f5f526a6c5aa8ffdda055a4d1";
6180 6153 };
6181 6154 };
6182 "resolve-1.9.0" = {
6155 "resolve-1.10.1" = {
6183 6156 name = "resolve";
6184 6157 packageName = "resolve";
6185 version = "1.9.0";
6186 src = fetchurl {
6187 url = "https://registry.npmjs.org/resolve/-/resolve-1.9.0.tgz";
6188 sha512 = "TZNye00tI67lwYvzxCxHGjwTNlUV70io54/Ed4j6PscB8xVfuBJpRenI/o6dVk0cY0PYTY27AgCoGGxRnYuItQ==";
6158 version = "1.10.1";
6159 src = fetchurl {
6160 url = "https://registry.npmjs.org/resolve/-/resolve-1.10.1.tgz";
6161 sha512 = "KuIe4mf++td/eFb6wkaPbMDnP6kObCaEtIDuHOUED6MNUo4K670KZUHuuvYPZDxNF0WVLw49n06M2m2dXphEzA==";
6189 6162 };
6190 6163 };
6191 6164 "resolve-cwd-2.0.0" = {
@@ -6332,22 +6305,22 b' let'
6332 6305 sha1 = "0e7350acdec80b1108528786ec1d4418d11b396d";
6333 6306 };
6334 6307 };
6335 "semver-5.6.0" = {
6308 "semver-5.7.0" = {
6336 6309 name = "semver";
6337 6310 packageName = "semver";
6338 version = "5.6.0";
6339 src = fetchurl {
6340 url = "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz";
6341 sha512 = "RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==";
6342 };
6343 };
6344 "serialize-javascript-1.6.1" = {
6311 version = "5.7.0";
6312 src = fetchurl {
6313 url = "https://registry.npmjs.org/semver/-/semver-5.7.0.tgz";
6314 sha512 = "Ya52jSX2u7QKghxeoFGpLwCtGlt7j0oY9DYb5apt9nPlJ42ID+ulTXESnt/qAQcoSERyZ5sl3LDIOw0nAn/5DA==";
6315 };
6316 };
6317 "serialize-javascript-1.7.0" = {
6345 6318 name = "serialize-javascript";
6346 6319 packageName = "serialize-javascript";
6347 version = "1.6.1";
6348 src = fetchurl {
6349 url = "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-1.6.1.tgz";
6350 sha512 = "A5MOagrPFga4YaKQSWHryl7AXvbQkEqpw4NNYMTNYUNV51bA8ABHgYFpqKx+YFFrw59xMV1qGH1R4AgoNIVgCw==";
6320 version = "1.7.0";
6321 src = fetchurl {
6322 url = "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-1.7.0.tgz";
6323 sha512 = "ke8UG8ulpFOxO8f8gRYabHQe/ZntKlcig2Mp+8+URDP1D8vJZ0KUt7LYo07q25Z/+JVSgpr/cui9PIp5H6/+nA==";
6351 6324 };
6352 6325 };
6353 6326 "set-blocking-2.0.0" = {
@@ -6593,13 +6566,13 b' let'
6593 6566 sha1 = "04e6926f662895354f3dd015203633b857297e2c";
6594 6567 };
6595 6568 };
6596 "sshpk-1.16.0" = {
6569 "sshpk-1.16.1" = {
6597 6570 name = "sshpk";
6598 6571 packageName = "sshpk";
6599 version = "1.16.0";
6600 src = fetchurl {
6601 url = "https://registry.npmjs.org/sshpk/-/sshpk-1.16.0.tgz";
6602 sha512 = "Zhev35/y7hRMcID/upReIvRse+I9SVhyVre/KTJSJQWMz3C3+G+HpO7m1wK/yckEtujKZ7dS4hkVxAnmHaIGVQ==";
6572 version = "1.16.1";
6573 src = fetchurl {
6574 url = "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz";
6575 sha512 = "HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==";
6603 6576 };
6604 6577 };
6605 6578 "ssri-5.3.0" = {
@@ -6629,13 +6602,13 b' let'
6629 6602 sha1 = "142bf6b64c2b416e4b707ebf8f09b8b5a5043877";
6630 6603 };
6631 6604 };
6632 "stream-browserify-2.0.1" = {
6605 "stream-browserify-2.0.2" = {
6633 6606 name = "stream-browserify";
6634 6607 packageName = "stream-browserify";
6635 version = "2.0.1";
6636 src = fetchurl {
6637 url = "https://registry.npmjs.org/stream-browserify/-/stream-browserify-2.0.1.tgz";
6638 sha1 = "66266ee5f9bdb9940a4e4514cafb43bb71e5c9db";
6608 version = "2.0.2";
6609 src = fetchurl {
6610 url = "https://registry.npmjs.org/stream-browserify/-/stream-browserify-2.0.2.tgz";
6611 sha512 = "nX6hmklHs/gr2FuxYDltq8fJA1GDlxKQCz8O/IM4atRqBH8OORmBNgfvW5gG10GT/qQ9u0CzIvr2X5Pkt6ntqg==";
6639 6612 };
6640 6613 };
6641 6614 "stream-each-1.2.3" = {
@@ -6836,13 +6809,13 b' let'
6836 6809 sha512 = "2wsvQ+4GwBvLPLWsNfLCDYGsW6xb7aeC6utq2Qh0PFwgEy7K7dsma9Jsmb2zSQj7GvYAyUGSntLtsv++GmgL1A==";
6837 6810 };
6838 6811 };
6839 "tapable-1.1.1" = {
6812 "tapable-1.1.3" = {
6840 6813 name = "tapable";
6841 6814 packageName = "tapable";
6842 version = "1.1.1";
6843 src = fetchurl {
6844 url = "https://registry.npmjs.org/tapable/-/tapable-1.1.1.tgz";
6845 sha512 = "9I2ydhj8Z9veORCw5PRm4u9uebCn0mcCa6scWoNcbZ6dAtoo2618u9UUzxgmsCOreJpqDDuv61LvwofW7hLcBA==";
6815 version = "1.1.3";
6816 src = fetchurl {
6817 url = "https://registry.npmjs.org/tapable/-/tapable-1.1.3.tgz";
6818 sha512 = "4WK/bYZmj8xLr+HUCODHGF1ZFzsYffasLUgEiMBY4fgtltdO6B4WJtlSbPaDTLpYTcGVwM2qLnFTICEcNxs3kA==";
6846 6819 };
6847 6820 };
6848 6821 "through-2.3.8" = {
@@ -6872,13 +6845,13 b' let'
6872 6845 sha512 = "YvC1SV1XdOUaL6gx5CoGroT3Gu49pK9+TZ38ErPldOWW4j49GI1HKs9DV+KGq/w6y+LZ72W1c8cKz2vzY+qpzg==";
6873 6846 };
6874 6847 };
6875 "tiny-emitter-2.0.2" = {
6848 "tiny-emitter-2.1.0" = {
6876 6849 name = "tiny-emitter";
6877 6850 packageName = "tiny-emitter";
6878 version = "2.0.2";
6879 src = fetchurl {
6880 url = "https://registry.npmjs.org/tiny-emitter/-/tiny-emitter-2.0.2.tgz";
6881 sha512 = "2NM0auVBGft5tee/OxP4PI3d8WItkDM+fPnaRAVo6xTDI2knbz9eC5ArWGqtGlYqiH3RU5yMpdyTTO7MguC4ow==";
6851 version = "2.1.0";
6852 src = fetchurl {
6853 url = "https://registry.npmjs.org/tiny-emitter/-/tiny-emitter-2.1.0.tgz";
6854 sha512 = "NB6Dk1A9xgQPMoGqC5CVXn123gWyte215ONT5Pp5a0yt4nlEoO1ZWeCwpncaekPHXO60i47ihFnZPiRPjRMq4Q==";
6882 6855 };
6883 6856 };
6884 6857 "tiny-lr-fork-0.0.5" = {
@@ -7034,13 +7007,13 b' let'
7034 7007 sha1 = "29c5733148057bb4e1f75df35b7a9cb72e6a59dd";
7035 7008 };
7036 7009 };
7037 "uglify-js-3.4.9" = {
7010 "uglify-js-3.4.10" = {
7038 7011 name = "uglify-js";
7039 7012 packageName = "uglify-js";
7040 version = "3.4.9";
7041 src = fetchurl {
7042 url = "https://registry.npmjs.org/uglify-js/-/uglify-js-3.4.9.tgz";
7043 sha512 = "8CJsbKOtEbnJsTyv6LE6m6ZKniqMiFWmm9sRbopbkGs3gMPPfd3Fh8iIA4Ykv5MgaTbqHr4BaoGLJLZNhsrW1Q==";
7013 version = "3.4.10";
7014 src = fetchurl {
7015 url = "https://registry.npmjs.org/uglify-js/-/uglify-js-3.4.10.tgz";
7016 sha512 = "Y2VsbPVs0FIshJztycsO2SfPk7/KAF/T72qzv9u5EpQ4kB2hQoHlhNQTsNyy6ul7lQtqJN/AoWeS23OzEiEFxw==";
7044 7017 };
7045 7018 };
7046 7019 "uglify-to-browserify-1.0.2" = {
@@ -7160,13 +7133,13 b' let'
7160 7133 sha1 = "8376873f7d2335179ffb1e6fc3a8ed0dfc8ab559";
7161 7134 };
7162 7135 };
7163 "upath-1.1.0" = {
7136 "upath-1.1.2" = {
7164 7137 name = "upath";
7165 7138 packageName = "upath";
7166 version = "1.1.0";
7167 src = fetchurl {
7168 url = "https://registry.npmjs.org/upath/-/upath-1.1.0.tgz";
7169 sha512 = "bzpH/oBhoS/QI/YtbkqCg6VEiPYjSZtrHQM6/QnJS6OL9pKUFLqb3aFh4Scvwm45+7iAgiMkLhSbaZxUqmrprw==";
7139 version = "1.1.2";
7140 src = fetchurl {
7141 url = "https://registry.npmjs.org/upath/-/upath-1.1.2.tgz";
7142 sha512 = "kXpym8nmDmlCBr7nKdIx8P2jNBa+pBpIUFRnKJ4dr8htyYGJFokkr2ZvERRtUN+9SY+JqXouNgUPtv6JQva/2Q==";
7170 7143 };
7171 7144 };
7172 7145 "upper-case-1.1.3" = {
@@ -7223,13 +7196,13 b' let'
7223 7196 sha1 = "7afb1afe50805246489e3db7fe0ed379336ac0f9";
7224 7197 };
7225 7198 };
7226 "util-0.10.4" = {
7199 "util-0.11.1" = {
7227 7200 name = "util";
7228 7201 packageName = "util";
7229 version = "0.10.4";
7230 src = fetchurl {
7231 url = "https://registry.npmjs.org/util/-/util-0.10.4.tgz";
7232 sha512 = "0Pm9hTQ3se5ll1XihRic3FDIku70C+iHUdT/W926rSgHV5QgXsYbKZN8MSC3tJtSkhuROzvsQjAaFENRXr+19A==";
7202 version = "0.11.1";
7203 src = fetchurl {
7204 url = "https://registry.npmjs.org/util/-/util-0.11.1.tgz";
7205 sha512 = "HShAsny+zS2TZfaXxD9tYj4HQGlBezXZMZuM/S5PKLLoZkShZiGk9o5CzukI1LVHZvjdvZ2Sj1aW/Ndn2NB/HQ==";
7233 7206 };
7234 7207 };
7235 7208 "util-deprecate-1.0.2" = {
@@ -7268,31 +7241,31 b' let'
7268 7241 sha512 = "yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==";
7269 7242 };
7270 7243 };
7271 "v8-compile-cache-2.0.2" = {
7244 "v8-compile-cache-2.0.3" = {
7272 7245 name = "v8-compile-cache";
7273 7246 packageName = "v8-compile-cache";
7274 version = "2.0.2";
7275 src = fetchurl {
7276 url = "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.0.2.tgz";
7277 sha512 = "1wFuMUIM16MDJRCrpbpuEPTUGmM5QMUg0cr3KFwra2XgOgFcPGDQHDh3CszSCD2Zewc/dh/pamNEW8CbfDebUw==";
7278 };
7279 };
7280 "v8flags-3.1.2" = {
7247 version = "2.0.3";
7248 src = fetchurl {
7249 url = "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.0.3.tgz";
7250 sha512 = "CNmdbwQMBjwr9Gsmohvm0pbL954tJrNzf6gWL3K+QMQf00PF7ERGrEiLgjuU3mKreLC2MeGhUsNV9ybTbLgd3w==";
7251 };
7252 };
7253 "v8flags-3.1.3" = {
7281 7254 name = "v8flags";
7282 7255 packageName = "v8flags";
7283 version = "3.1.2";
7284 src = fetchurl {
7285 url = "https://registry.npmjs.org/v8flags/-/v8flags-3.1.2.tgz";
7286 sha512 = "MtivA7GF24yMPte9Rp/BWGCYQNaUj86zeYxV/x2RRJMKagImbbv3u8iJC57lNhWLPcGLJmHcHmFWkNsplbbLWw==";
7287 };
7288 };
7289 "vendors-1.0.2" = {
7256 version = "3.1.3";
7257 src = fetchurl {
7258 url = "https://registry.npmjs.org/v8flags/-/v8flags-3.1.3.tgz";
7259 sha512 = "amh9CCg3ZxkzQ48Mhcb8iX7xpAfYJgePHxWMQCBWECpOSqJUXgY26ncA61UTV0BkPqfhcy6mzwCIoP4ygxpW8w==";
7260 };
7261 };
7262 "vendors-1.0.3" = {
7290 7263 name = "vendors";
7291 7264 packageName = "vendors";
7292 version = "1.0.2";
7293 src = fetchurl {
7294 url = "https://registry.npmjs.org/vendors/-/vendors-1.0.2.tgz";
7295 sha512 = "w/hry/368nO21AN9QljsaIhb9ZiZtZARoVH5f3CsFbawdLdayCgKRPup7CggujvySMxx0I91NOyxdVENohprLQ==";
7265 version = "1.0.3";
7266 src = fetchurl {
7267 url = "https://registry.npmjs.org/vendors/-/vendors-1.0.3.tgz";
7268 sha512 = "fOi47nsJP5Wqefa43kyWSg80qF+Q3XA6MUkgi7Hp1HQaKDQW4cQrK2D0P7mmbFtsV1N89am55Yru/nyEwRubcw==";
7296 7269 };
7297 7270 };
7298 7271 "verror-1.10.0" = {
@@ -7430,13 +7403,13 b' let'
7430 7403 sha1 = "b79669bb42ecb409f83d583cad52ca17eaa1643f";
7431 7404 };
7432 7405 };
7433 "worker-farm-1.6.0" = {
7406 "worker-farm-1.7.0" = {
7434 7407 name = "worker-farm";
7435 7408 packageName = "worker-farm";
7436 version = "1.6.0";
7437 src = fetchurl {
7438 url = "https://registry.npmjs.org/worker-farm/-/worker-farm-1.6.0.tgz";
7439 sha512 = "6w+3tHbM87WnSWnENBUvA2pxJPLhQUg5LKwUQHq3r+XPhIM+Gh2R5ycbwPCyuGbNg+lPgdcnQUhuC02kJCvffQ==";
7409 version = "1.7.0";
7410 src = fetchurl {
7411 url = "https://registry.npmjs.org/worker-farm/-/worker-farm-1.7.0.tgz";
7412 sha512 = "rvw3QTZc8lAxyVrqcSGVm5yP/IJ2UcB3U0graE3LCFoZ0Yn2x4EoVSqJKdB/T5M+FLcRPjz4TDacRf3OCfNUzw==";
7440 7413 };
7441 7414 };
7442 7415 "wrap-ansi-2.1.0" = {
@@ -7536,14 +7509,14 b' let'
7536 7509 sources."@polymer/paper-behaviors-3.0.1"
7537 7510 sources."@polymer/paper-button-3.0.1"
7538 7511 sources."@polymer/paper-ripple-3.0.1"
7539 sources."@polymer/paper-spinner-3.0.1"
7512 sources."@polymer/paper-spinner-3.0.2"
7540 7513 sources."@polymer/paper-styles-3.0.1"
7541 7514 sources."@polymer/paper-toast-3.0.1"
7542 7515 sources."@polymer/paper-toggle-button-3.0.1"
7543 7516 sources."@polymer/paper-tooltip-3.0.1"
7544 sources."@polymer/polymer-3.1.0"
7517 sources."@polymer/polymer-3.2.0"
7545 7518 sources."@types/clone-0.1.30"
7546 sources."@types/node-6.14.2"
7519 sources."@types/node-6.14.6"
7547 7520 sources."@types/parse5-2.2.34"
7548 7521 sources."@webassemblyjs/ast-1.7.10"
7549 7522 sources."@webassemblyjs/floating-point-hex-parser-1.7.10"
@@ -7563,8 +7536,8 b' let'
7563 7536 sources."@webassemblyjs/wasm-parser-1.7.10"
7564 7537 sources."@webassemblyjs/wast-parser-1.7.10"
7565 7538 sources."@webassemblyjs/wast-printer-1.7.10"
7566 sources."@webcomponents/shadycss-1.7.1"
7567 sources."@webcomponents/webcomponentsjs-2.2.1"
7539 sources."@webcomponents/shadycss-1.9.1"
7540 sources."@webcomponents/webcomponentsjs-2.2.10"
7568 7541 sources."@xtuc/ieee754-1.2.0"
7569 7542 sources."@xtuc/long-4.2.1"
7570 7543 sources."abbrev-1.1.1"
@@ -7576,7 +7549,7 b' let'
7576 7549 ];
7577 7550 })
7578 7551 sources."ajv-4.11.8"
7579 sources."ajv-keywords-3.2.0"
7552 sources."ajv-keywords-3.4.0"
7580 7553 (sources."align-text-0.1.4" // {
7581 7554 dependencies = [
7582 7555 sources."kind-of-3.2.2"
@@ -7586,7 +7559,11 b' let'
7586 7559 sources."amdefine-1.0.1"
7587 7560 sources."ansi-regex-0.2.1"
7588 7561 sources."ansi-styles-1.1.0"
7589 sources."anymatch-2.0.0"
7562 (sources."anymatch-2.0.0" // {
7563 dependencies = [
7564 sources."normalize-path-2.1.1"
7565 ];
7566 })
7590 7567 sources."appenlight-client-git+https://git@github.com/AppEnlight/appenlight-client-js.git#0.5.1"
7591 7568 sources."aproba-1.2.0"
7592 7569 (sources."argparse-0.1.16" // {
@@ -7602,11 +7579,10 b' let'
7602 7579 sources."array-union-1.0.2"
7603 7580 sources."array-uniq-1.0.3"
7604 7581 sources."array-unique-0.3.2"
7605 sources."arrify-1.0.1"
7606 7582 sources."asap-2.0.6"
7607 7583 sources."asn1-0.2.4"
7608 7584 sources."asn1.js-4.10.1"
7609 (sources."assert-1.4.1" // {
7585 (sources."assert-1.5.0" // {
7610 7586 dependencies = [
7611 7587 sources."inherits-2.0.1"
7612 7588 sources."util-0.10.3"
@@ -7616,7 +7592,7 b' let'
7616 7592 sources."assign-symbols-1.0.0"
7617 7593 sources."ast-types-0.9.6"
7618 7594 sources."async-0.1.22"
7619 sources."async-each-1.0.1"
7595 sources."async-each-1.0.3"
7620 7596 sources."asynckit-0.4.0"
7621 7597 sources."atob-2.1.2"
7622 7598 (sources."autoprefixer-6.7.7" // {
@@ -7738,8 +7714,8 b' let'
7738 7714 sources."base64-js-1.3.0"
7739 7715 sources."bcrypt-pbkdf-1.0.2"
7740 7716 sources."big.js-5.2.2"
7741 sources."binary-extensions-1.12.0"
7742 sources."bluebird-3.5.3"
7717 sources."binary-extensions-1.13.1"
7718 sources."bluebird-3.5.4"
7743 7719 sources."bn.js-4.11.8"
7744 7720 sources."boolbase-1.0.0"
7745 7721 sources."boom-2.10.1"
@@ -7763,7 +7739,7 b' let'
7763 7739 sources."builtin-status-codes-3.0.0"
7764 7740 (sources."cacache-10.0.4" // {
7765 7741 dependencies = [
7766 sources."glob-7.1.3"
7742 sources."glob-7.1.4"
7767 7743 sources."graceful-fs-4.1.15"
7768 7744 sources."lru-cache-4.1.5"
7769 7745 sources."minimatch-3.0.4"
@@ -7772,20 +7748,20 b' let'
7772 7748 })
7773 7749 sources."cache-base-1.0.1"
7774 7750 sources."camel-case-3.0.0"
7775 sources."camelcase-5.0.0"
7751 sources."camelcase-5.3.1"
7776 7752 (sources."caniuse-api-1.6.1" // {
7777 7753 dependencies = [
7778 7754 sources."browserslist-1.7.7"
7779 7755 ];
7780 7756 })
7781 sources."caniuse-db-1.0.30000927"
7782 sources."caniuse-lite-1.0.30000927"
7757 sources."caniuse-db-1.0.30000967"
7758 sources."caniuse-lite-1.0.30000967"
7783 7759 sources."caseless-0.12.0"
7784 7760 sources."center-align-0.1.3"
7785 7761 sources."chalk-0.5.1"
7786 (sources."chokidar-2.0.4" // {
7787 dependencies = [
7788 sources."is-glob-4.0.0"
7762 (sources."chokidar-2.1.5" // {
7763 dependencies = [
7764 sources."is-glob-4.0.1"
7789 7765 ];
7790 7766 })
7791 7767 sources."chownr-1.1.1"
@@ -7825,7 +7801,7 b' let'
7825 7801 })
7826 7802 (sources."cli-1.0.1" // {
7827 7803 dependencies = [
7828 sources."glob-7.1.3"
7804 sources."glob-7.1.4"
7829 7805 sources."minimatch-3.0.4"
7830 7806 ];
7831 7807 })
@@ -7848,10 +7824,10 b' let'
7848 7824 sources."color-string-0.3.0"
7849 7825 sources."colormin-1.1.2"
7850 7826 sources."colors-0.6.2"
7851 sources."combined-stream-1.0.7"
7827 sources."combined-stream-1.0.8"
7852 7828 sources."commander-2.14.1"
7853 7829 sources."commondir-1.0.1"
7854 sources."component-emitter-1.2.1"
7830 sources."component-emitter-1.3.0"
7855 7831 sources."concat-map-0.0.1"
7856 7832 (sources."concat-stream-1.6.2" // {
7857 7833 dependencies = [
@@ -7864,7 +7840,7 b' let'
7864 7840 sources."convert-source-map-1.6.0"
7865 7841 (sources."copy-concurrently-1.0.5" // {
7866 7842 dependencies = [
7867 sources."glob-7.1.3"
7843 sources."glob-7.1.4"
7868 7844 sources."minimatch-3.0.4"
7869 7845 sources."rimraf-2.6.3"
7870 7846 ];
@@ -7872,11 +7848,11 b' let'
7872 7848 sources."copy-descriptor-0.1.1"
7873 7849 (sources."copy-webpack-plugin-4.6.0" // {
7874 7850 dependencies = [
7875 sources."is-glob-4.0.0"
7851 sources."is-glob-4.0.1"
7876 7852 sources."minimatch-3.0.4"
7877 7853 ];
7878 7854 })
7879 sources."core-js-2.6.1"
7855 sources."core-js-2.6.5"
7880 7856 sources."core-util-is-1.0.2"
7881 7857 sources."create-ecdh-4.0.3"
7882 7858 sources."create-hash-1.2.0"
@@ -7896,7 +7872,7 b' let'
7896 7872 sources."regexpu-core-1.0.0"
7897 7873 ];
7898 7874 })
7899 sources."css-what-2.1.2"
7875 sources."css-what-2.1.3"
7900 7876 sources."cssesc-0.1.0"
7901 7877 sources."cssnano-3.10.0"
7902 7878 sources."csso-2.3.2"
@@ -7921,11 +7897,10 b' let'
7921 7897 sources."detect-file-1.0.0"
7922 7898 sources."detect-indent-4.0.0"
7923 7899 sources."diffie-hellman-5.0.3"
7924 sources."dir-glob-2.0.0"
7900 sources."dir-glob-2.2.2"
7925 7901 sources."dom-converter-0.2.0"
7926 (sources."dom-serializer-0.1.0" // {
7927 dependencies = [
7928 sources."domelementtype-1.1.3"
7902 (sources."dom-serializer-0.1.1" // {
7903 dependencies = [
7929 7904 sources."entities-1.1.2"
7930 7905 ];
7931 7906 })
@@ -7939,14 +7914,15 b' let'
7939 7914 sources."domelementtype-1.3.1"
7940 7915 sources."domhandler-2.3.0"
7941 7916 sources."domutils-1.5.1"
7942 (sources."duplexify-3.6.1" // {
7917 sources."dropzone-5.5.1"
7918 (sources."duplexify-3.7.1" // {
7943 7919 dependencies = [
7944 7920 sources."readable-stream-2.3.6"
7945 7921 sources."string_decoder-1.1.1"
7946 7922 ];
7947 7923 })
7948 7924 sources."ecc-jsbn-0.1.2"
7949 sources."electron-to-chromium-1.3.98"
7925 sources."electron-to-chromium-1.3.133"
7950 7926 sources."elliptic-6.4.1"
7951 7927 sources."emojis-list-2.1.0"
7952 7928 sources."end-of-stream-1.4.1"
@@ -7961,14 +7937,14 b' let'
7961 7937 sources."es-to-primitive-1.2.0"
7962 7938 sources."es6-templates-0.2.3"
7963 7939 sources."escape-string-regexp-1.0.5"
7964 sources."eslint-scope-4.0.0"
7940 sources."eslint-scope-4.0.3"
7965 7941 sources."espree-3.5.4"
7966 7942 sources."esprima-1.0.4"
7967 7943 sources."esrecurse-4.2.1"
7968 7944 sources."estraverse-4.2.0"
7969 7945 sources."esutils-2.0.2"
7970 7946 sources."eventemitter2-0.4.14"
7971 sources."events-1.1.1"
7947 sources."events-3.0.0"
7972 7948 sources."evp_bytestokey-1.0.3"
7973 7949 sources."execa-1.0.0"
7974 7950 sources."exit-0.1.2"
@@ -8025,10 +8001,10 b' let'
8025 8001 sources."minimatch-0.3.0"
8026 8002 ];
8027 8003 })
8028 sources."fined-1.1.1"
8004 sources."fined-1.2.0"
8029 8005 sources."flagged-respawn-1.0.1"
8030 8006 sources."flatten-1.0.2"
8031 (sources."flush-write-stream-1.0.3" // {
8007 (sources."flush-write-stream-1.1.1" // {
8032 8008 dependencies = [
8033 8009 sources."readable-stream-2.3.6"
8034 8010 sources."string_decoder-1.1.1"
@@ -8051,7 +8027,7 b' let'
8051 8027 ];
8052 8028 })
8053 8029 sources."fs.realpath-1.0.0"
8054 sources."fsevents-1.2.4"
8030 sources."fsevents-1.2.9"
8055 8031 sources."function-bind-1.1.1"
8056 8032 sources."gaze-0.5.2"
8057 8033 sources."get-caller-file-1.0.3"
@@ -8083,7 +8059,7 b' let'
8083 8059 sources."globals-9.18.0"
8084 8060 (sources."globby-7.1.1" // {
8085 8061 dependencies = [
8086 sources."glob-7.1.3"
8062 sources."glob-7.1.4"
8087 8063 sources."minimatch-3.0.4"
8088 8064 ];
8089 8065 })
@@ -8115,12 +8091,18 b' let'
8115 8091 sources."supports-color-2.0.0"
8116 8092 ];
8117 8093 })
8118 sources."grunt-contrib-jshint-0.12.0"
8094 (sources."grunt-contrib-jshint-0.12.0" // {
8095 dependencies = [
8096 sources."jshint-2.9.7"
8097 sources."lodash-4.17.11"
8098 sources."minimatch-3.0.4"
8099 ];
8100 })
8119 8101 (sources."grunt-contrib-less-1.4.1" // {
8120 8102 dependencies = [
8121 8103 sources."ansi-regex-2.1.1"
8122 8104 sources."ansi-styles-2.2.1"
8123 sources."async-2.6.1"
8105 sources."async-2.6.2"
8124 8106 sources."chalk-1.1.3"
8125 8107 sources."has-ansi-2.0.0"
8126 8108 sources."lodash-4.17.11"
@@ -8172,7 +8154,7 b' let'
8172 8154 sources."hmac-drbg-1.0.1"
8173 8155 sources."hoek-2.16.3"
8174 8156 sources."home-or-tmp-2.0.0"
8175 sources."homedir-polyfill-1.0.1"
8157 sources."homedir-polyfill-1.0.3"
8176 8158 sources."hooker-0.2.3"
8177 8159 sources."html-comment-regex-1.1.2"
8178 8160 sources."html-loader-0.4.5"
@@ -8203,7 +8185,7 b' let'
8203 8185 sources."supports-color-5.5.0"
8204 8186 ];
8205 8187 })
8206 sources."ieee754-1.1.12"
8188 sources."ieee754-1.1.13"
8207 8189 sources."iferr-0.1.5"
8208 8190 sources."ignore-3.3.10"
8209 8191 sources."image-size-0.5.5"
@@ -8211,9 +8193,9 b' let'
8211 8193 dependencies = [
8212 8194 sources."find-up-3.0.0"
8213 8195 sources."locate-path-3.0.0"
8214 sources."p-limit-2.1.0"
8196 sources."p-limit-2.2.0"
8215 8197 sources."p-locate-3.0.0"
8216 sources."p-try-2.0.0"
8198 sources."p-try-2.2.0"
8217 8199 sources."pkg-dir-3.0.0"
8218 8200 ];
8219 8201 })
@@ -8261,12 +8243,12 b' let'
8261 8243 sources."isobject-3.0.1"
8262 8244 sources."isstream-0.1.2"
8263 8245 sources."jquery-1.11.3"
8264 sources."js-base64-2.5.0"
8246 sources."js-base64-2.5.1"
8265 8247 sources."js-tokens-3.0.2"
8266 8248 sources."js-yaml-2.0.5"
8267 8249 sources."jsbn-0.1.1"
8268 8250 sources."jsesc-1.3.0"
8269 (sources."jshint-2.9.7" // {
8251 (sources."jshint-2.10.2" // {
8270 8252 dependencies = [
8271 8253 sources."lodash-4.17.11"
8272 8254 sources."minimatch-3.0.4"
@@ -8297,12 +8279,11 b' let'
8297 8279 sources."findup-sync-2.0.0"
8298 8280 ];
8299 8281 })
8300 sources."loader-runner-2.3.1"
8282 sources."loader-runner-2.4.0"
8301 8283 sources."loader-utils-1.2.3"
8302 8284 sources."locate-path-2.0.0"
8303 8285 sources."lodash-0.9.2"
8304 8286 sources."lodash.camelcase-4.3.0"
8305 sources."lodash.debounce-4.0.8"
8306 8287 sources."lodash.isplainobject-4.0.6"
8307 8288 sources."lodash.memoize-4.1.2"
8308 8289 sources."lodash.uniq-4.5.0"
@@ -8318,7 +8299,7 b' let'
8318 8299 sources."mark.js-8.11.1"
8319 8300 sources."math-expression-evaluator-1.2.17"
8320 8301 sources."md5.js-1.3.5"
8321 sources."mem-4.0.0"
8302 sources."mem-4.3.0"
8322 8303 (sources."memory-fs-0.4.1" // {
8323 8304 dependencies = [
8324 8305 sources."readable-stream-2.3.6"
@@ -8328,9 +8309,9 b' let'
8328 8309 sources."micromatch-3.1.10"
8329 8310 sources."miller-rabin-4.0.1"
8330 8311 sources."mime-1.6.0"
8331 sources."mime-db-1.37.0"
8332 sources."mime-types-2.1.21"
8333 sources."mimic-fn-1.2.0"
8312 sources."mime-db-1.40.0"
8313 sources."mime-types-2.1.24"
8314 sources."mimic-fn-2.1.0"
8334 8315 sources."minimalistic-assert-1.0.1"
8335 8316 sources."minimalistic-crypto-utils-1.0.1"
8336 8317 sources."minimatch-0.2.14"
@@ -8346,22 +8327,22 b' let'
8346 8327 sources."minimist-0.0.8"
8347 8328 ];
8348 8329 })
8349 sources."moment-2.23.0"
8350 sources."mousetrap-1.6.2"
8330 sources."moment-2.24.0"
8331 sources."mousetrap-1.6.3"
8351 8332 (sources."move-concurrently-1.0.1" // {
8352 8333 dependencies = [
8353 sources."glob-7.1.3"
8334 sources."glob-7.1.4"
8354 8335 sources."minimatch-3.0.4"
8355 8336 sources."rimraf-2.6.3"
8356 8337 ];
8357 8338 })
8358 8339 sources."ms-2.0.0"
8359 sources."nan-2.12.1"
8340 sources."nan-2.13.2"
8360 8341 sources."nanomatch-1.2.13"
8361 sources."neo-async-2.6.0"
8342 sources."neo-async-2.6.1"
8362 8343 sources."nice-try-1.0.5"
8363 8344 sources."no-case-2.3.2"
8364 (sources."node-libs-browser-2.1.0" // {
8345 (sources."node-libs-browser-2.2.0" // {
8365 8346 dependencies = [
8366 8347 (sources."readable-stream-2.3.6" // {
8367 8348 dependencies = [
@@ -8377,7 +8358,7 b' let'
8377 8358 sources."nopt-2.0.0"
8378 8359 ];
8379 8360 })
8380 sources."normalize-path-2.1.1"
8361 sources."normalize-path-3.0.0"
8381 8362 sources."normalize-range-0.1.2"
8382 8363 sources."normalize-url-1.9.1"
8383 8364 sources."npm-run-path-2.0.2"
@@ -8399,7 +8380,7 b' let'
8399 8380 sources."kind-of-3.2.2"
8400 8381 ];
8401 8382 })
8402 sources."object-keys-1.0.12"
8383 sources."object-keys-1.1.1"
8403 8384 sources."object-visit-1.0.1"
8404 8385 sources."object.defaults-1.1.0"
8405 8386 sources."object.getownpropertydescriptors-2.0.3"
@@ -8413,11 +8394,11 b' let'
8413 8394 sources."osenv-0.1.5"
8414 8395 sources."p-defer-1.0.0"
8415 8396 sources."p-finally-1.0.0"
8416 sources."p-is-promise-1.1.0"
8397 sources."p-is-promise-2.1.0"
8417 8398 sources."p-limit-1.3.0"
8418 8399 sources."p-locate-2.0.0"
8419 8400 sources."p-try-1.0.0"
8420 sources."pako-1.0.7"
8401 sources."pako-1.0.10"
8421 8402 (sources."parallel-transform-1.1.0" // {
8422 8403 dependencies = [
8423 8404 sources."readable-stream-2.3.6"
@@ -8425,7 +8406,7 b' let'
8425 8406 ];
8426 8407 })
8427 8408 sources."param-case-2.1.1"
8428 sources."parse-asn1-5.1.1"
8409 sources."parse-asn1-5.1.4"
8429 8410 sources."parse-filepath-1.0.2"
8430 8411 sources."parse-passwd-1.0.0"
8431 8412 sources."parse5-3.0.3"
@@ -8564,7 +8545,7 b' let'
8564 8545 sources."query-string-4.3.4"
8565 8546 sources."querystring-0.2.0"
8566 8547 sources."querystring-es3-0.2.1"
8567 sources."randombytes-2.0.6"
8548 sources."randombytes-2.1.0"
8568 8549 sources."randomfill-1.0.4"
8569 8550 sources."raw-loader-1.0.0-beta.0"
8570 8551 (sources."readable-stream-1.1.14" // {
@@ -8608,14 +8589,9 b' let'
8608 8589 })
8609 8590 sources."relateurl-0.2.7"
8610 8591 sources."remove-trailing-separator-1.1.0"
8611 (sources."renderkid-2.0.2" // {
8592 (sources."renderkid-2.0.3" // {
8612 8593 dependencies = [
8613 8594 sources."ansi-regex-2.1.1"
8614 sources."domhandler-2.1.0"
8615 sources."domutils-1.1.6"
8616 sources."htmlparser2-3.3.0"
8617 sources."isarray-0.0.1"
8618 sources."readable-stream-1.0.34"
8619 8595 sources."strip-ansi-3.0.1"
8620 8596 ];
8621 8597 })
@@ -8625,7 +8601,7 b' let'
8625 8601 sources."request-2.81.0"
8626 8602 sources."require-directory-2.1.1"
8627 8603 sources."require-main-filename-1.0.1"
8628 sources."resolve-1.9.0"
8604 sources."resolve-1.10.1"
8629 8605 sources."resolve-cwd-2.0.0"
8630 8606 sources."resolve-dir-1.0.1"
8631 8607 sources."resolve-from-3.0.0"
@@ -8641,12 +8617,12 b' let'
8641 8617 sources."sax-1.2.4"
8642 8618 (sources."schema-utils-0.4.7" // {
8643 8619 dependencies = [
8644 sources."ajv-6.6.2"
8620 sources."ajv-6.10.0"
8645 8621 ];
8646 8622 })
8647 8623 sources."select-1.1.2"
8648 sources."semver-5.6.0"
8649 sources."serialize-javascript-1.6.1"
8624 sources."semver-5.7.0"
8625 sources."serialize-javascript-1.7.0"
8650 8626 sources."set-blocking-2.0.0"
8651 8627 (sources."set-value-2.0.0" // {
8652 8628 dependencies = [
@@ -8698,7 +8674,7 b' let'
8698 8674 sources."source-map-url-0.4.0"
8699 8675 sources."split-string-3.1.0"
8700 8676 sources."sprintf-js-1.0.3"
8701 (sources."sshpk-1.16.0" // {
8677 (sources."sshpk-1.16.1" // {
8702 8678 dependencies = [
8703 8679 sources."assert-plus-1.0.0"
8704 8680 ];
@@ -8722,7 +8698,7 b' let'
8722 8698 ];
8723 8699 })
8724 8700 sources."sticky-sidebar-3.3.1"
8725 (sources."stream-browserify-2.0.1" // {
8701 (sources."stream-browserify-2.0.2" // {
8726 8702 dependencies = [
8727 8703 sources."readable-stream-2.3.6"
8728 8704 sources."string_decoder-1.1.1"
@@ -8759,7 +8735,7 b' let'
8759 8735 sources."js-yaml-3.7.0"
8760 8736 ];
8761 8737 })
8762 sources."tapable-1.1.1"
8738 sources."tapable-1.1.3"
8763 8739 sources."through-2.3.8"
8764 8740 (sources."through2-2.0.5" // {
8765 8741 dependencies = [
@@ -8768,7 +8744,7 b' let'
8768 8744 ];
8769 8745 })
8770 8746 sources."timers-browserify-2.0.10"
8771 sources."tiny-emitter-2.0.2"
8747 sources."tiny-emitter-2.1.0"
8772 8748 (sources."tiny-lr-fork-0.0.5" // {
8773 8749 dependencies = [
8774 8750 sources."debug-0.7.4"
@@ -8808,9 +8784,9 b' let'
8808 8784 sources."source-map-0.6.1"
8809 8785 ];
8810 8786 })
8811 (sources."uglify-js-3.4.9" // {
8812 dependencies = [
8813 sources."commander-2.17.1"
8787 (sources."uglify-js-3.4.10" // {
8788 dependencies = [
8789 sources."commander-2.19.0"
8814 8790 sources."source-map-0.6.1"
8815 8791 ];
8816 8792 })
@@ -8843,7 +8819,7 b' let'
8843 8819 sources."has-values-0.1.4"
8844 8820 ];
8845 8821 })
8846 sources."upath-1.1.0"
8822 sources."upath-1.1.2"
8847 8823 sources."upper-case-1.1.3"
8848 8824 (sources."uri-js-4.2.2" // {
8849 8825 dependencies = [
@@ -8857,14 +8833,14 b' let'
8857 8833 ];
8858 8834 })
8859 8835 sources."use-3.1.1"
8860 sources."util-0.10.4"
8836 sources."util-0.11.1"
8861 8837 sources."util-deprecate-1.0.2"
8862 8838 sources."util.promisify-1.0.0"
8863 8839 sources."utila-0.4.0"
8864 8840 sources."uuid-3.3.2"
8865 sources."v8-compile-cache-2.0.2"
8866 sources."v8flags-3.1.2"
8867 sources."vendors-1.0.2"
8841 sources."v8-compile-cache-2.0.3"
8842 sources."v8flags-3.1.3"
8843 sources."vendors-1.0.3"
8868 8844 (sources."verror-1.10.0" // {
8869 8845 dependencies = [
8870 8846 sources."assert-plus-1.0.0"
@@ -8879,7 +8855,7 b' let'
8879 8855 sources."waypoints-4.0.1"
8880 8856 (sources."webpack-4.23.1" // {
8881 8857 dependencies = [
8882 sources."ajv-6.6.2"
8858 sources."ajv-6.10.0"
8883 8859 ];
8884 8860 })
8885 8861 (sources."webpack-cli-3.1.2" // {
@@ -8919,7 +8895,7 b' let'
8919 8895 sources."which-module-2.0.0"
8920 8896 sources."window-size-0.1.0"
8921 8897 sources."wordwrap-0.0.2"
8922 sources."worker-farm-1.6.0"
8898 sources."worker-farm-1.7.0"
8923 8899 (sources."wrap-ansi-2.1.0" // {
8924 8900 dependencies = [
8925 8901 sources."ansi-regex-2.1.1"
@@ -8935,9 +8911,9 b' let'
8935 8911 dependencies = [
8936 8912 sources."find-up-3.0.0"
8937 8913 sources."locate-path-3.0.0"
8938 sources."p-limit-2.1.0"
8914 sources."p-limit-2.2.0"
8939 8915 sources."p-locate-3.0.0"
8940 sources."p-try-2.0.0"
8916 sources."p-try-2.2.0"
8941 8917 ];
8942 8918 })
8943 8919 sources."yargs-parser-11.1.1"
@@ -35,6 +35,18 b' self: super: {'
35 35 ];
36 36 });
37 37
38 "cffi" = super."cffi".override (attrs: {
39 buildInputs = [
40 pkgs.libffi
41 ];
42 });
43
44 "cryptography" = super."cryptography".override (attrs: {
45 buildInputs = [
46 pkgs.openssl
47 ];
48 });
49
38 50 "gevent" = super."gevent".override (attrs: {
39 51 propagatedBuildInputs = attrs.propagatedBuildInputs ++ [
40 52 # NOTE: (marcink) odd requirements from gevent aren't set properly,
@@ -152,12 +164,6 b' self: super: {'
152 164 };
153 165 });
154 166
155 "pytest-runner" = super."pytest-runner".override (attrs: {
156 propagatedBuildInputs = [
157 self."setuptools-scm"
158 ];
159 });
160
161 167 "python-ldap" = super."python-ldap".override (attrs: {
162 168 propagatedBuildInputs = attrs.propagatedBuildInputs ++ [
163 169 pkgs.openldap
@@ -5,7 +5,7 b''
5 5
6 6 self: super: {
7 7 "alembic" = super.buildPythonPackage {
8 name = "alembic-1.0.5";
8 name = "alembic-1.0.10";
9 9 doCheck = false;
10 10 propagatedBuildInputs = [
11 11 self."sqlalchemy"
@@ -14,8 +14,8 b' self: super: {'
14 14 self."python-dateutil"
15 15 ];
16 16 src = fetchurl {
17 url = "https://files.pythonhosted.org/packages/1c/65/b8e4f5b2f345bb13b5e0a3fddd892b0b3f0e8ad4880e954fdc6a50d00d84/alembic-1.0.5.tar.gz";
18 sha256 = "0rpjqp2iq6p49x1nli18ivak1izz547nnjxi110mzrgc1v7dxzz9";
17 url = "https://files.pythonhosted.org/packages/6e/8b/fa3bd058cccd5e9177fea4efa26bfb769228fdd3178436ad5e05830ef6ef/alembic-1.0.10.tar.gz";
18 sha256 = "1dwl0264r6ri2jyrjr68am04x538ab26xwy4crqjnnhm4alwm3c2";
19 19 };
20 20 meta = {
21 21 license = [ pkgs.lib.licenses.mit ];
@@ -51,6 +51,17 b' self: super: {'
51 51 license = [ pkgs.lib.licenses.bsdOriginal ];
52 52 };
53 53 };
54 "asn1crypto" = super.buildPythonPackage {
55 name = "asn1crypto-0.24.0";
56 doCheck = false;
57 src = fetchurl {
58 url = "https://files.pythonhosted.org/packages/fc/f1/8db7daa71f414ddabfa056c4ef792e1461ff655c2ae2928a2b675bfed6b4/asn1crypto-0.24.0.tar.gz";
59 sha256 = "0jaf8rf9dx1lf23xfv2cdd5h52f1qr3w8k63985bc35g3d220p4x";
60 };
61 meta = {
62 license = [ pkgs.lib.licenses.mit ];
63 };
64 };
54 65 "atomicwrites" = super.buildPythonPackage {
55 66 name = "atomicwrites-1.2.1";
56 67 doCheck = false;
@@ -77,8 +88,8 b' self: super: {'
77 88 name = "authomatic-0.1.0.post1";
78 89 doCheck = false;
79 90 src = fetchurl {
80 url = "https://code.rhodecode.com/upstream/authomatic/archive/90a9ce60cc405ae8a2bf5c3713acd5d78579a04e.tar.gz?md5=3c68720a1322b25254009518d1ff6801";
81 sha256 = "1cgk0a86sbsjbri06gf5z5l4npwkjdxw6fdnwl4vvfmxs2sx9yxw";
91 url = "https://code.rhodecode.com/upstream/authomatic/artifacts/download/0-4fe9c041-a567-4f84-be4c-7efa2a606d3c.tar.gz?md5=f6bdc3c769688212db68233e8d2b0383";
92 sha256 = "0pc716mva0ym6xd8jwzjbjp8dqxy9069wwwv2aqwb8lyhl4757ab";
82 93 };
83 94 meta = {
84 95 license = [ pkgs.lib.licenses.mit ];
@@ -146,15 +157,15 b' self: super: {'
146 157 };
147 158 };
148 159 "bleach" = super.buildPythonPackage {
149 name = "bleach-3.0.2";
160 name = "bleach-3.1.0";
150 161 doCheck = false;
151 162 propagatedBuildInputs = [
152 163 self."six"
153 164 self."webencodings"
154 165 ];
155 166 src = fetchurl {
156 url = "https://files.pythonhosted.org/packages/ae/31/680afc7d44040004296a2d8f0584983c2f2386448cd9d0964197e6c1160e/bleach-3.0.2.tar.gz";
157 sha256 = "06474zg7f73hv8h1xw2wcsmvn2ygj73zxgxxqg8zcx8ap1srdls8";
167 url = "https://files.pythonhosted.org/packages/78/5a/0df03e8735cd9c75167528299c738702437589b9c71a849489d00ffa82e8/bleach-3.1.0.tar.gz";
168 sha256 = "1yhrgrhkln8bd6gn3imj69g1h4xqah9gaz9q26crqr6gmmvpzprz";
158 169 };
159 170 meta = {
160 171 license = [ pkgs.lib.licenses.asl20 ];
@@ -187,6 +198,20 b' self: super: {'
187 198 license = [ pkgs.lib.licenses.bsdOriginal ];
188 199 };
189 200 };
201 "cffi" = super.buildPythonPackage {
202 name = "cffi-1.12.2";
203 doCheck = false;
204 propagatedBuildInputs = [
205 self."pycparser"
206 ];
207 src = fetchurl {
208 url = "https://files.pythonhosted.org/packages/64/7c/27367b38e6cc3e1f49f193deb761fe75cda9f95da37b67b422e62281fcac/cffi-1.12.2.tar.gz";
209 sha256 = "19qfks2djya8vix95bmg3xzipjb8w9b8mbj4j5k2hqkc8j58f4z1";
210 };
211 meta = {
212 license = [ pkgs.lib.licenses.mit ];
213 };
214 };
190 215 "chameleon" = super.buildPythonPackage {
191 216 name = "chameleon-2.24";
192 217 doCheck = false;
@@ -230,7 +255,7 b' self: super: {'
230 255 };
231 256 };
232 257 "colander" = super.buildPythonPackage {
233 name = "colander-1.5.1";
258 name = "colander-1.7.0";
234 259 doCheck = false;
235 260 propagatedBuildInputs = [
236 261 self."translationstring"
@@ -238,8 +263,8 b' self: super: {'
238 263 self."enum34"
239 264 ];
240 265 src = fetchurl {
241 url = "https://files.pythonhosted.org/packages/ec/d1/fcca811a0a692c69d27e36b4d11a73acb98b4bab48323442642b6fd4386d/colander-1.5.1.tar.gz";
242 sha256 = "18ah4cwwxnpm6qxi6x9ipy51dal4spd343h44s5wd01cnhgrwsyq";
266 url = "https://files.pythonhosted.org/packages/db/e4/74ab06f54211917b41865cafc987ce511e35503de48da9bfe9358a1bdc3e/colander-1.7.0.tar.gz";
267 sha256 = "1wl1bqab307lbbcjx81i28s3yl6dlm4rf15fxawkjb6j48x1cn6p";
243 268 };
244 269 meta = {
245 270 license = [ { fullName = "BSD-derived (http://www.repoze.org/LICENSE.txt)"; } ];
@@ -252,19 +277,19 b' self: super: {'
252 277 self."six"
253 278 ];
254 279 src = fetchurl {
255 url = "https://code.rhodecode.com/upstream/configobj/archive/a11ff0a0bd4fbda9e3a91267e720f88329efb4a6.tar.gz?md5=9916c524ea11a6c418217af6b28d4b3c";
256 sha256 = "1hhcxirwvg58grlfr177b3awhbq8hlx1l3lh69ifl1ki7lfd1s1x";
280 url = "https://code.rhodecode.com/upstream/configobj/artifacts/download/0-012de99a-b1e1-4f64-a5c0-07a98a41b324.tar.gz?md5=6a513f51fe04b2c18cf84c1395a7c626";
281 sha256 = "0kqfrdfr14mw8yd8qwq14dv2xghpkjmd3yjsy8dfcbvpcc17xnxp";
257 282 };
258 283 meta = {
259 284 license = [ pkgs.lib.licenses.bsdOriginal ];
260 285 };
261 286 };
262 287 "configparser" = super.buildPythonPackage {
263 name = "configparser-3.7.1";
288 name = "configparser-3.7.4";
264 289 doCheck = false;
265 290 src = fetchurl {
266 url = "https://files.pythonhosted.org/packages/b6/a6/eceea7c5a5dbcf56815bed411c38cabd8a879386be10717b160e7362b5a2/configparser-3.7.1.tar.gz";
267 sha256 = "0cnz213il9lhgda6x70fw7mfqr8da43s3wm343lwzhqx94mgmmav";
291 url = "https://files.pythonhosted.org/packages/e2/1c/83fd53748d8245cb9a3399f705c251d3fc0ce7df04450aac1cfc49dd6a0f/configparser-3.7.4.tar.gz";
292 sha256 = "0xac32886ihs2xg7w1gppcq2sgin5qsm8lqwijs5xifq9w0x0q6s";
268 293 };
269 294 meta = {
270 295 license = [ pkgs.lib.licenses.mit ];
@@ -285,16 +310,34 b' self: super: {'
285 310 };
286 311 };
287 312 "coverage" = super.buildPythonPackage {
288 name = "coverage-4.5.1";
313 name = "coverage-4.5.3";
289 314 doCheck = false;
290 315 src = fetchurl {
291 url = "https://files.pythonhosted.org/packages/35/fe/e7df7289d717426093c68d156e0fd9117c8f4872b6588e8a8928a0f68424/coverage-4.5.1.tar.gz";
292 sha256 = "1wbrzpxka3xd4nmmkc6q0ir343d91kymwsm8pbmwa0d2a7q4ir2n";
316 url = "https://files.pythonhosted.org/packages/82/70/2280b5b29a0352519bb95ab0ef1ea942d40466ca71c53a2085bdeff7b0eb/coverage-4.5.3.tar.gz";
317 sha256 = "02f6m073qdispn96rc616hg0rnmw1pgqzw3bgxwiwza4zf9hirlx";
293 318 };
294 319 meta = {
295 320 license = [ pkgs.lib.licenses.asl20 ];
296 321 };
297 322 };
323 "cryptography" = super.buildPythonPackage {
324 name = "cryptography-2.6.1";
325 doCheck = false;
326 propagatedBuildInputs = [
327 self."asn1crypto"
328 self."six"
329 self."cffi"
330 self."enum34"
331 self."ipaddress"
332 ];
333 src = fetchurl {
334 url = "https://files.pythonhosted.org/packages/07/ca/bc827c5e55918ad223d59d299fff92f3563476c3b00d0a9157d9c0217449/cryptography-2.6.1.tar.gz";
335 sha256 = "19iwz5avym5zl6jrrrkym1rdaa9h61j20ph4cswsqgv8xg5j3j16";
336 };
337 meta = {
338 license = [ pkgs.lib.licenses.bsdOriginal { fullName = "BSD or Apache License, Version 2.0"; } pkgs.lib.licenses.asl20 ];
339 };
340 };
298 341 "cssselect" = super.buildPythonPackage {
299 342 name = "cssselect-1.0.3";
300 343 doCheck = false;
@@ -337,11 +380,11 b' self: super: {'
337 380 };
338 381 };
339 382 "defusedxml" = super.buildPythonPackage {
340 name = "defusedxml-0.5.0";
383 name = "defusedxml-0.6.0";
341 384 doCheck = false;
342 385 src = fetchurl {
343 url = "https://files.pythonhosted.org/packages/74/ba/4ba4e89e21b5a2e267d80736ea674609a0a33cc4435a6d748ef04f1f9374/defusedxml-0.5.0.tar.gz";
344 sha256 = "1x54n0h8hl92vvwyymx883fbqpqjwn2mc8fb383bcg3z9zwz5mr4";
386 url = "https://files.pythonhosted.org/packages/a4/5f/f8aa58ca0cf01cbcee728abc9d88bfeb74e95e6cb4334cfd5bed5673ea77/defusedxml-0.6.0.tar.gz";
387 sha256 = "1xbp8fivl3wlbyg2jrvs4lalaqv1xp9a9f29p75wdx2s2d6h717n";
345 388 };
346 389 meta = {
347 390 license = [ pkgs.lib.licenses.psfl ];
@@ -399,11 +442,11 b' self: super: {'
399 442 };
400 443 };
401 444 "ecdsa" = super.buildPythonPackage {
402 name = "ecdsa-0.13";
445 name = "ecdsa-0.13.2";
403 446 doCheck = false;
404 447 src = fetchurl {
405 url = "https://files.pythonhosted.org/packages/f9/e5/99ebb176e47f150ac115ffeda5fedb6a3dbb3c00c74a59fd84ddf12f5857/ecdsa-0.13.tar.gz";
406 sha256 = "1yj31j0asmrx4an9xvsaj2icdmzy6pw0glfpqrrkrphwdpi1xkv4";
448 url = "https://files.pythonhosted.org/packages/51/76/139bf6e9b7b6684d5891212cdbd9e0739f2bfc03f380a1a6ffa700f392ac/ecdsa-0.13.2.tar.gz";
449 sha256 = "116qaq7bh4lcynzi613960jhsnn19v0kmsqwahiwjfj14gx4y0sw";
407 450 };
408 451 meta = {
409 452 license = [ pkgs.lib.licenses.mit ];
@@ -491,8 +534,8 b' self: super: {'
491 534 self."configparser"
492 535 ];
493 536 src = fetchurl {
494 url = "https://code.rhodecode.com/upstream/entrypoints/archive/96e6d645684e1af3d7df5b5272f3fe85a546b233.tar.gz?md5=7db37771aea9ac9fefe093e5d6987313";
495 sha256 = "0bihrdp8ahsys437kxdhk52gz6kib8rxjv71i93wkw7594fcaxll";
537 url = "https://code.rhodecode.com/upstream/entrypoints/artifacts/download/0-8e9ee9e4-c4db-409c-b07e-81568fd1832d.tar.gz?md5=3a027b8ff1d257b91fe257de6c43357d";
538 sha256 = "0qih72n2myclanplqipqxpgpj9d2yhff1pz5d02zq1cfqyd173w5";
496 539 };
497 540 meta = {
498 541 license = [ pkgs.lib.licenses.mit ];
@@ -623,11 +666,11 b' self: super: {'
623 666 };
624 667 };
625 668 "hupper" = super.buildPythonPackage {
626 name = "hupper-1.4.2";
669 name = "hupper-1.6.1";
627 670 doCheck = false;
628 671 src = fetchurl {
629 url = "https://files.pythonhosted.org/packages/f1/75/1915dc7650b4867fa3049256e24ca8eddb5989998fcec788cf52b9812dfc/hupper-1.4.2.tar.gz";
630 sha256 = "16vb9fkiaakdpcp6pn56h3w0dwvm67bxq2k2dv4i382qhqwphdzb";
672 url = "https://files.pythonhosted.org/packages/85/d9/e005d357b11249c5d70ddf5b7adab2e4c0da4e8b0531ff146917a04fe6c0/hupper-1.6.1.tar.gz";
673 sha256 = "0d3cvkc8ssgwk54wvhbifj56ry97qi10pfzwfk8vwzzcikbfp3zy";
631 674 };
632 675 meta = {
633 676 license = [ pkgs.lib.licenses.mit ];
@@ -671,15 +714,15 b' self: super: {'
671 714 };
672 715 };
673 716 "ipdb" = super.buildPythonPackage {
674 name = "ipdb-0.11";
717 name = "ipdb-0.12";
675 718 doCheck = false;
676 719 propagatedBuildInputs = [
677 720 self."setuptools"
678 721 self."ipython"
679 722 ];
680 723 src = fetchurl {
681 url = "https://files.pythonhosted.org/packages/80/fe/4564de08f174f3846364b3add8426d14cebee228f741c27e702b2877e85b/ipdb-0.11.tar.gz";
682 sha256 = "02m0l8wrhhd3z7dg3czn5ys1g5pxib516hpshdzp7rxzsxgcd0bh";
724 url = "https://files.pythonhosted.org/packages/6d/43/c3c2e866a8803e196d6209595020a4a6db1a3c5d07c01455669497ae23d0/ipdb-0.12.tar.gz";
725 sha256 = "1khr2n7xfy8hg65kj1bsrjq9g7656pp0ybfa8abpbzpdawji3qnw";
683 726 };
684 727 meta = {
685 728 license = [ pkgs.lib.licenses.bsdOriginal ];
@@ -802,14 +845,14 b' self: super: {'
802 845 };
803 846 };
804 847 "jupyter-core" = super.buildPythonPackage {
805 name = "jupyter-core-4.4.0";
848 name = "jupyter-core-4.5.0";
806 849 doCheck = false;
807 850 propagatedBuildInputs = [
808 851 self."traitlets"
809 852 ];
810 853 src = fetchurl {
811 url = "https://files.pythonhosted.org/packages/b6/2d/2804f4de3a95583f65e5dcb4d7c8c7183124882323758996e867f47e72af/jupyter_core-4.4.0.tar.gz";
812 sha256 = "1dy083rarba8prn9f9srxq3c7n7vyql02ycrqq306c40lr57aw5s";
854 url = "https://files.pythonhosted.org/packages/4a/de/ff4ca734656d17ebe0450807b59d728f45277e2e7f4b82bc9aae6cb82961/jupyter_core-4.5.0.tar.gz";
855 sha256 = "1xr4pbghwk5hayn5wwnhb7z95380r45p79gf5if5pi1akwg7qvic";
813 856 };
814 857 meta = {
815 858 license = [ pkgs.lib.licenses.bsdOriginal ];
@@ -1008,14 +1051,14 b' self: super: {'
1008 1051 };
1009 1052 };
1010 1053 "paste" = super.buildPythonPackage {
1011 name = "paste-3.0.5";
1054 name = "paste-3.0.8";
1012 1055 doCheck = false;
1013 1056 propagatedBuildInputs = [
1014 1057 self."six"
1015 1058 ];
1016 1059 src = fetchurl {
1017 url = "https://files.pythonhosted.org/packages/d4/41/91bde422400786b1b06357c1e6e3a5379f54dc3002aeb337cb767233304e/Paste-3.0.5.tar.gz";
1018 sha256 = "1a6i8fh1fg8r4x800fvy9r82m15clwjim6yf2g9r4dff0y40dchv";
1060 url = "https://files.pythonhosted.org/packages/66/65/e3acf1663438483c1f6ced0b6c6f3b90da9f0faacb0a6e2aa0f3f9f4b235/Paste-3.0.8.tar.gz";
1061 sha256 = "05w1sh6ky4d7pmdb8nv82n13w22jcn3qsagg5ih3hjmbws9kkwf4";
1019 1062 };
1020 1063 meta = {
1021 1064 license = [ pkgs.lib.licenses.mit ];
@@ -1033,7 +1076,7 b' self: super: {'
1033 1076 };
1034 1077 };
1035 1078 "pastescript" = super.buildPythonPackage {
1036 name = "pastescript-3.0.0";
1079 name = "pastescript-3.1.0";
1037 1080 doCheck = false;
1038 1081 propagatedBuildInputs = [
1039 1082 self."paste"
@@ -1041,23 +1084,23 b' self: super: {'
1041 1084 self."six"
1042 1085 ];
1043 1086 src = fetchurl {
1044 url = "https://files.pythonhosted.org/packages/08/2a/3797377a884ab9a064ad4d564ed612e54d26d7997caa8229c9c9df4eac31/PasteScript-3.0.0.tar.gz";
1045 sha256 = "1hvmyz1sbn7ws1syw567ph7km9fi0wi75r3vlyzx6sk0z26xkm6r";
1087 url = "https://files.pythonhosted.org/packages/9e/1d/14db1c283eb21a5d36b6ba1114c13b709629711e64acab653d9994fe346f/PasteScript-3.1.0.tar.gz";
1088 sha256 = "02qcxjjr32ks7a6d4f533wl34ysc7yhwlrfcyqwqbzr52250v4fs";
1046 1089 };
1047 1090 meta = {
1048 1091 license = [ pkgs.lib.licenses.mit ];
1049 1092 };
1050 1093 };
1051 1094 "pathlib2" = super.buildPythonPackage {
1052 name = "pathlib2-2.3.3";
1095 name = "pathlib2-2.3.4";
1053 1096 doCheck = false;
1054 1097 propagatedBuildInputs = [
1055 1098 self."six"
1056 1099 self."scandir"
1057 1100 ];
1058 1101 src = fetchurl {
1059 url = "https://files.pythonhosted.org/packages/bf/d7/a2568f4596b75d2c6e2b4094a7e64f620decc7887f69a1f2811931ea15b9/pathlib2-2.3.3.tar.gz";
1060 sha256 = "0hpp92vqqgcd8h92msm9slv161b1q160igjwnkf2ag6cx0c96695";
1102 url = "https://files.pythonhosted.org/packages/b5/f4/9c7cc726ece2498b6c8b62d3262aa43f59039b953fe23c9964ac5e18d40b/pathlib2-2.3.4.tar.gz";
1103 sha256 = "1y0f9rkm1924zrc5dn4bwxlhgdkbml82lkcc28l5rgmr7d918q24";
1061 1104 };
1062 1105 meta = {
1063 1106 license = [ pkgs.lib.licenses.mit ];
@@ -1075,14 +1118,14 b' self: super: {'
1075 1118 };
1076 1119 };
1077 1120 "pexpect" = super.buildPythonPackage {
1078 name = "pexpect-4.6.0";
1121 name = "pexpect-4.7.0";
1079 1122 doCheck = false;
1080 1123 propagatedBuildInputs = [
1081 1124 self."ptyprocess"
1082 1125 ];
1083 1126 src = fetchurl {
1084 url = "https://files.pythonhosted.org/packages/89/43/07d07654ee3e25235d8cea4164cdee0ec39d1fda8e9203156ebe403ffda4/pexpect-4.6.0.tar.gz";
1085 sha256 = "1fla85g47iaxxpjhp9vkxdnv4pgc7rplfy6ja491smrrk0jqi3ia";
1127 url = "https://files.pythonhosted.org/packages/1c/b1/362a0d4235496cb42c33d1d8732b5e2c607b0129ad5fdd76f5a583b9fcb3/pexpect-4.7.0.tar.gz";
1128 sha256 = "1sv2rri15zwhds85a4kamwh9pj49qcxv7m4miyr4jfpfwv81yb4y";
1086 1129 };
1087 1130 meta = {
1088 1131 license = [ pkgs.lib.licenses.isc { fullName = "ISC License (ISCL)"; } ];
@@ -1117,63 +1160,63 b' self: super: {'
1117 1160 };
1118 1161 };
1119 1162 "plaster-pastedeploy" = super.buildPythonPackage {
1120 name = "plaster-pastedeploy-0.6";
1163 name = "plaster-pastedeploy-0.7";
1121 1164 doCheck = false;
1122 1165 propagatedBuildInputs = [
1123 1166 self."pastedeploy"
1124 1167 self."plaster"
1125 1168 ];
1126 1169 src = fetchurl {
1127 url = "https://files.pythonhosted.org/packages/3f/e7/6a6833158d2038ec40085433308a1e164fd1dac595513f6dd556d5669bb8/plaster_pastedeploy-0.6.tar.gz";
1128 sha256 = "1bkggk18f4z2bmsmxyxabvf62znvjwbivzh880419r3ap0616cf2";
1170 url = "https://files.pythonhosted.org/packages/99/69/2d3bc33091249266a1bd3cf24499e40ab31d54dffb4a7d76fe647950b98c/plaster_pastedeploy-0.7.tar.gz";
1171 sha256 = "1zg7gcsvc1kzay1ry5p699rg2qavfsxqwl17mqxzr0gzw6j9679r";
1129 1172 };
1130 1173 meta = {
1131 1174 license = [ pkgs.lib.licenses.mit ];
1132 1175 };
1133 1176 };
1134 1177 "pluggy" = super.buildPythonPackage {
1135 name = "pluggy-0.8.1";
1178 name = "pluggy-0.11.0";
1136 1179 doCheck = false;
1137 1180 src = fetchurl {
1138 url = "https://files.pythonhosted.org/packages/38/e1/83b10c17688af7b2998fa5342fec58ecbd2a5a7499f31e606ae6640b71ac/pluggy-0.8.1.tar.gz";
1139 sha256 = "05l6g42p9ilmabw0hlbiyxy6gyzjri41m5l11a8dzgvi77q35p4d";
1181 url = "https://files.pythonhosted.org/packages/0d/a1/862ab336e8128fde20981d2c1aa8506693412daf5083b1911d539412676b/pluggy-0.11.0.tar.gz";
1182 sha256 = "10511a54dvafw1jrk75mrhml53c7b7w4yaw7241696lc2hfvr895";
1140 1183 };
1141 1184 meta = {
1142 1185 license = [ pkgs.lib.licenses.mit ];
1143 1186 };
1144 1187 };
1145 1188 "prompt-toolkit" = super.buildPythonPackage {
1146 name = "prompt-toolkit-1.0.15";
1189 name = "prompt-toolkit-1.0.16";
1147 1190 doCheck = false;
1148 1191 propagatedBuildInputs = [
1149 1192 self."six"
1150 1193 self."wcwidth"
1151 1194 ];
1152 1195 src = fetchurl {
1153 url = "https://files.pythonhosted.org/packages/8a/ad/cf6b128866e78ad6d7f1dc5b7f99885fb813393d9860778b2984582e81b5/prompt_toolkit-1.0.15.tar.gz";
1154 sha256 = "05v9h5nydljwpj5nm8n804ms0glajwfy1zagrzqrg91wk3qqi1c5";
1196 url = "https://files.pythonhosted.org/packages/f1/03/bb36771dc9fa7553ac4bdc639a9ecdf6fda0ff4176faf940d97e3c16e41d/prompt_toolkit-1.0.16.tar.gz";
1197 sha256 = "1d65hm6nf0cbq0q0121m60zzy4s1fpg9fn761s1yxf08dridvkn1";
1155 1198 };
1156 1199 meta = {
1157 1200 license = [ pkgs.lib.licenses.bsdOriginal ];
1158 1201 };
1159 1202 };
1160 1203 "psutil" = super.buildPythonPackage {
1161 name = "psutil-5.4.8";
1204 name = "psutil-5.5.1";
1162 1205 doCheck = false;
1163 1206 src = fetchurl {
1164 url = "https://files.pythonhosted.org/packages/e3/58/0eae6e4466e5abf779d7e2b71fac7fba5f59e00ea36ddb3ed690419ccb0f/psutil-5.4.8.tar.gz";
1165 sha256 = "1hyna338sml2cl1mfb2gs89np18z27mvyhmq4ifh22x07n7mq9kf";
1207 url = "https://files.pythonhosted.org/packages/c7/01/7c30b247cdc5ba29623faa5c8cf1f1bbf7e041783c340414b0ed7e067c64/psutil-5.5.1.tar.gz";
1208 sha256 = "045qaqvn6k90bj5bcy259yrwcd2afgznaav3sfhphy9b8ambzkkj";
1166 1209 };
1167 1210 meta = {
1168 1211 license = [ pkgs.lib.licenses.bsdOriginal ];
1169 1212 };
1170 1213 };
1171 1214 "psycopg2" = super.buildPythonPackage {
1172 name = "psycopg2-2.7.5";
1215 name = "psycopg2-2.8.3";
1173 1216 doCheck = false;
1174 1217 src = fetchurl {
1175 url = "https://files.pythonhosted.org/packages/b2/c1/7bf6c464e903ffc4f3f5907c389e5a4199666bf57f6cd6bf46c17912a1f9/psycopg2-2.7.5.tar.gz";
1176 sha256 = "17klx964gw8z0znl0raz3by8vdc7cq5gxj4pdcrfcina84nrdkzc";
1218 url = "https://files.pythonhosted.org/packages/5c/1c/6997288da181277a0c29bc39a5f9143ff20b8c99f2a7d059cfb55163e165/psycopg2-2.8.3.tar.gz";
1219 sha256 = "0ms4kx0p5n281l89awccix4d05ybmdngnjjpi9jbzd0rhf1nwyl9";
1177 1220 };
1178 1221 meta = {
1179 1222 license = [ pkgs.lib.licenses.zpl21 { fullName = "GNU Library or Lesser General Public License (LGPL)"; } { fullName = "LGPL with exceptions or ZPL"; } ];
@@ -1239,14 +1282,25 b' self: super: {'
1239 1282 };
1240 1283 };
1241 1284 "pyasn1-modules" = super.buildPythonPackage {
1242 name = "pyasn1-modules-0.2.4";
1285 name = "pyasn1-modules-0.2.5";
1243 1286 doCheck = false;
1244 1287 propagatedBuildInputs = [
1245 1288 self."pyasn1"
1246 1289 ];
1247 1290 src = fetchurl {
1248 url = "https://files.pythonhosted.org/packages/bd/a5/ef7bf693e8a8f015386c9167483199f54f8a8ec01d1c737e05524f16e792/pyasn1-modules-0.2.4.tar.gz";
1249 sha256 = "0z3w5dqrrvdplg9ma45j8n23xvyrj9ki8mg4ibqbn7l4qpl90855";
1291 url = "https://files.pythonhosted.org/packages/ec/0b/69620cb04a016e4a1e8e352e8a42717862129b574b3479adb2358a1f12f7/pyasn1-modules-0.2.5.tar.gz";
1292 sha256 = "15nvfx0vnl8akdlv3k6s0n80vqvryj82bm040jdsn7wmyxl1ywpg";
1293 };
1294 meta = {
1295 license = [ pkgs.lib.licenses.bsdOriginal ];
1296 };
1297 };
1298 "pycparser" = super.buildPythonPackage {
1299 name = "pycparser-2.19";
1300 doCheck = false;
1301 src = fetchurl {
1302 url = "https://files.pythonhosted.org/packages/68/9e/49196946aee219aead1290e00d1e7fdeab8567783e83e1b9ab5585e6206a/pycparser-2.19.tar.gz";
1303 sha256 = "1cr5dcj9628lkz1qlwq3fv97c25363qppkmcayqvd05dpy573259";
1250 1304 };
1251 1305 meta = {
1252 1306 license = [ pkgs.lib.licenses.bsdOriginal ];
@@ -1274,23 +1328,12 b' self: super: {'
1274 1328 license = [ pkgs.lib.licenses.mit { fullName = "LGPL/MIT"; } { fullName = "GNU Library or Lesser General Public License (LGPL)"; } ];
1275 1329 };
1276 1330 };
1277 "pyflakes" = super.buildPythonPackage {
1278 name = "pyflakes-0.8.1";
1331 "pygments" = super.buildPythonPackage {
1332 name = "pygments-2.4.2";
1279 1333 doCheck = false;
1280 1334 src = fetchurl {
1281 url = "https://files.pythonhosted.org/packages/75/22/a90ec0252f4f87f3ffb6336504de71fe16a49d69c4538dae2f12b9360a38/pyflakes-0.8.1.tar.gz";
1282 sha256 = "0sbpq6pqm1i9wqi41mlfrsc5rk92jv4mskvlyxmnhlbdnc80ma1z";
1283 };
1284 meta = {
1285 license = [ pkgs.lib.licenses.mit ];
1286 };
1287 };
1288 "pygments" = super.buildPythonPackage {
1289 name = "pygments-2.3.1";
1290 doCheck = false;
1291 src = fetchurl {
1292 url = "https://files.pythonhosted.org/packages/64/69/413708eaf3a64a6abb8972644e0f20891a55e621c6759e2c3f3891e05d63/Pygments-2.3.1.tar.gz";
1293 sha256 = "0ji87g09jph8jqcvclgb02qvxasdnr9pzvk90rl66d90yqcxmyjz";
1335 url = "https://files.pythonhosted.org/packages/7e/ae/26808275fc76bf2832deb10d3a3ed3107bc4de01b85dcccbe525f2cd6d1e/Pygments-2.4.2.tar.gz";
1336 sha256 = "15v2sqm5g12bqa0c7wikfh9ck2nl97ayizy1hpqhmws5gqalq748";
1294 1337 };
1295 1338 meta = {
1296 1339 license = [ pkgs.lib.licenses.bsdOriginal ];
@@ -1330,7 +1373,7 b' self: super: {'
1330 1373 };
1331 1374 };
1332 1375 "pyramid" = super.buildPythonPackage {
1333 name = "pyramid-1.10.1";
1376 name = "pyramid-1.10.4";
1334 1377 doCheck = false;
1335 1378 propagatedBuildInputs = [
1336 1379 self."hupper"
@@ -1345,28 +1388,13 b' self: super: {'
1345 1388 self."repoze.lru"
1346 1389 ];
1347 1390 src = fetchurl {
1348 url = "https://files.pythonhosted.org/packages/0a/3e/22e3ac9be1b70a01139adba8906ee4b8f628bb469fea3c52f6c97b73063c/pyramid-1.10.1.tar.gz";
1349 sha256 = "1h5105nfh6rsrfjiyw20aavyibj36la3hajy6vh1fa77xb4y3hrp";
1391 url = "https://files.pythonhosted.org/packages/c2/43/1ae701c9c6bb3a434358e678a5e72c96e8aa55cf4cb1d2fa2041b5dd38b7/pyramid-1.10.4.tar.gz";
1392 sha256 = "0rkxs1ajycg2zh1c94xlmls56mx5m161sn8112skj0amza6cn36q";
1350 1393 };
1351 1394 meta = {
1352 1395 license = [ { fullName = "Repoze Public License"; } { fullName = "BSD-derived (http://www.repoze.org/LICENSE.txt)"; } ];
1353 1396 };
1354 1397 };
1355 "pyramid-beaker" = super.buildPythonPackage {
1356 name = "pyramid-beaker-0.8";
1357 doCheck = false;
1358 propagatedBuildInputs = [
1359 self."pyramid"
1360 self."beaker"
1361 ];
1362 src = fetchurl {
1363 url = "https://files.pythonhosted.org/packages/d9/6e/b85426e00fd3d57f4545f74e1c3828552d8700f13ededeef9233f7bca8be/pyramid_beaker-0.8.tar.gz";
1364 sha256 = "0hflx3qkcdml1mwpq53sz46s7jickpfn0zy0ns2c7j445j66bp3p";
1365 };
1366 meta = {
1367 license = [ { fullName = "BSD-derived (http://www.repoze.org/LICENSE.txt)"; } ];
1368 };
1369 };
1370 1398 "pyramid-debugtoolbar" = super.buildPythonPackage {
1371 1399 name = "pyramid-debugtoolbar-4.5";
1372 1400 doCheck = false;
@@ -1538,14 +1566,14 b' self: super: {'
1538 1566 };
1539 1567 };
1540 1568 "python-dateutil" = super.buildPythonPackage {
1541 name = "python-dateutil-2.7.5";
1569 name = "python-dateutil-2.8.0";
1542 1570 doCheck = false;
1543 1571 propagatedBuildInputs = [
1544 1572 self."six"
1545 1573 ];
1546 1574 src = fetchurl {
1547 url = "https://files.pythonhosted.org/packages/0e/01/68747933e8d12263d41ce08119620d9a7e5eb72c876a3442257f74490da0/python-dateutil-2.7.5.tar.gz";
1548 sha256 = "00ngwcdw36w5b37b51mdwn3qxid9zdf3kpffv2q6n9kl05y2iyc8";
1575 url = "https://files.pythonhosted.org/packages/ad/99/5b2e99737edeb28c71bcbec5b5dda19d0d9ef3ca3e92e3e925e7c0bb364c/python-dateutil-2.8.0.tar.gz";
1576 sha256 = "17nsfhy4xdz1khrfxa61vd7pmvd5z0wa3zb6v4gb4kfnykv0b668";
1549 1577 };
1550 1578 meta = {
1551 1579 license = [ pkgs.lib.licenses.bsdOriginal pkgs.lib.licenses.asl20 { fullName = "Dual License"; } ];
@@ -1690,7 +1718,7 b' self: super: {'
1690 1718 };
1691 1719 };
1692 1720 "rhodecode-enterprise-ce" = super.buildPythonPackage {
1693 name = "rhodecode-enterprise-ce-4.16.2";
1721 name = "rhodecode-enterprise-ce-4.17.0";
1694 1722 buildInputs = [
1695 1723 self."pytest"
1696 1724 self."py"
@@ -1709,36 +1737,29 b' self: super: {'
1709 1737 ];
1710 1738 doCheck = true;
1711 1739 propagatedBuildInputs = [
1712 self."setuptools-scm"
1713 1740 self."amqp"
1714 1741 self."authomatic"
1715 self."atomicwrites"
1716 self."attrs"
1717 1742 self."babel"
1718 1743 self."beaker"
1719 1744 self."bleach"
1720 1745 self."celery"
1721 self."chameleon"
1722 1746 self."channelstream"
1723 1747 self."click"
1724 1748 self."colander"
1725 1749 self."configobj"
1726 1750 self."cssselect"
1751 self."cryptography"
1727 1752 self."decorator"
1728 1753 self."deform"
1729 1754 self."docutils"
1730 1755 self."dogpile.cache"
1731 1756 self."dogpile.core"
1732 self."ecdsa"
1733 1757 self."formencode"
1734 1758 self."future"
1735 1759 self."futures"
1736 self."gnureadline"
1737 1760 self."infrae.cache"
1738 1761 self."iso8601"
1739 1762 self."itsdangerous"
1740 self."jinja2"
1741 self."billiard"
1742 1763 self."kombu"
1743 1764 self."lxml"
1744 1765 self."mako"
@@ -1747,21 +1768,18 b' self: super: {'
1747 1768 self."msgpack-python"
1748 1769 self."pyotp"
1749 1770 self."packaging"
1771 self."pathlib2"
1750 1772 self."paste"
1751 1773 self."pastedeploy"
1752 1774 self."pastescript"
1753 self."pathlib2"
1754 1775 self."peppercorn"
1755 1776 self."psutil"
1756 1777 self."py-bcrypt"
1778 self."pycurl"
1757 1779 self."pycrypto"
1758 self."pycurl"
1759 self."pyflakes"
1760 1780 self."pygments"
1761 1781 self."pyparsing"
1762 self."pyramid-beaker"
1763 1782 self."pyramid-debugtoolbar"
1764 self."pyramid-jinja2"
1765 1783 self."pyramid-mako"
1766 1784 self."pyramid"
1767 1785 self."pyramid-mailer"
@@ -1784,7 +1802,6 b' self: super: {'
1784 1802 self."sshpubkeys"
1785 1803 self."subprocess32"
1786 1804 self."supervisor"
1787 self."tempita"
1788 1805 self."translationstring"
1789 1806 self."urllib3"
1790 1807 self."urlobject"
@@ -1813,7 +1830,6 b' self: super: {'
1813 1830 self."greenlet"
1814 1831 self."gunicorn"
1815 1832 self."waitress"
1816 self."setproctitle"
1817 1833 self."ipdb"
1818 1834 self."ipython"
1819 1835 self."rhodecode-tools"
@@ -1855,8 +1871,8 b' self: super: {'
1855 1871 self."elasticsearch1-dsl"
1856 1872 ];
1857 1873 src = fetchurl {
1858 url = "https://code.rhodecode.com/rhodecode-tools-ce/archive/v1.2.1.tar.gz?md5=25bc2f7de1da318e547236d3fb463d28";
1859 sha256 = "1k8l3s4mvshza1zay6dfxprq54fyb5dc85dqdva9wa3f466y0adk";
1874 url = "https://code.rhodecode.com/rhodecode-tools-ce/artifacts/download/0-10ac93f4-bb7d-4b97-baea-68110743dd5a.tar.gz?md5=962dc77c06aceee62282b98d33149661";
1875 sha256 = "1vfhgf46inbx7jvlfx4fdzh3vz7lh37r291gzb5hx447pfm3qllg";
1860 1876 };
1861 1877 meta = {
1862 1878 license = [ { fullName = "Apache 2.0 and Proprietary"; } ];
@@ -1878,11 +1894,11 b' self: super: {'
1878 1894 };
1879 1895 };
1880 1896 "scandir" = super.buildPythonPackage {
1881 name = "scandir-1.9.0";
1897 name = "scandir-1.10.0";
1882 1898 doCheck = false;
1883 1899 src = fetchurl {
1884 url = "https://files.pythonhosted.org/packages/16/2a/557af1181e6b4e30254d5a6163b18f5053791ca66e251e77ab08887e8fe3/scandir-1.9.0.tar.gz";
1885 sha256 = "0r3hvf1a9jm1rkqgx40gxkmccknkaiqjavs8lccgq9s8khh5x5s4";
1900 url = "https://files.pythonhosted.org/packages/df/f5/9c052db7bd54d0cbf1bc0bb6554362bba1012d03e5888950a4f5c5dadc4e/scandir-1.10.0.tar.gz";
1901 sha256 = "1bkqwmf056pkchf05ywbnf659wqlp6lljcdb0y88wr9f0vv32ijd";
1886 1902 };
1887 1903 meta = {
1888 1904 license = [ pkgs.lib.licenses.bsdOriginal { fullName = "New BSD License"; } ];
@@ -1900,22 +1916,11 b' self: super: {'
1900 1916 };
1901 1917 };
1902 1918 "setuptools" = super.buildPythonPackage {
1903 name = "setuptools-40.8.0";
1919 name = "setuptools-41.0.1";
1904 1920 doCheck = false;
1905 1921 src = fetchurl {
1906 url = "https://files.pythonhosted.org/packages/c2/f7/c7b501b783e5a74cf1768bc174ee4fb0a8a6ee5af6afa92274ff964703e0/setuptools-40.8.0.zip";
1907 sha256 = "0k9hifpgahnw2a26w3cr346iy733k6d3nwh3f7g9m13y6f8fqkkf";
1908 };
1909 meta = {
1910 license = [ pkgs.lib.licenses.mit ];
1911 };
1912 };
1913 "setuptools-scm" = super.buildPythonPackage {
1914 name = "setuptools-scm-2.1.0";
1915 doCheck = false;
1916 src = fetchurl {
1917 url = "https://files.pythonhosted.org/packages/e5/62/f9e1ac314464eb5945c97542acb6bf6f3381dfa5d7a658de7730c36f31a1/setuptools_scm-2.1.0.tar.gz";
1918 sha256 = "0yb364cgk15sfw3x8ln4ssh98z1dj6n8iiz4r2rw1cfsxhgi8rx7";
1922 url = "https://files.pythonhosted.org/packages/1d/64/a18a487b4391a05b9c7f938b94a16d80305bf0369c6b0b9509e86165e1d3/setuptools-41.0.1.zip";
1923 sha256 = "04sns22y2hhsrwfy1mha2lgslvpjsjsz8xws7h2rh5a7ylkd28m2";
1919 1924 };
1920 1925 meta = {
1921 1926 license = [ pkgs.lib.licenses.mit ];
@@ -1966,40 +1971,40 b' self: super: {'
1966 1971 };
1967 1972 };
1968 1973 "sshpubkeys" = super.buildPythonPackage {
1969 name = "sshpubkeys-2.2.0";
1974 name = "sshpubkeys-3.1.0";
1970 1975 doCheck = false;
1971 1976 propagatedBuildInputs = [
1972 self."pycrypto"
1977 self."cryptography"
1973 1978 self."ecdsa"
1974 1979 ];
1975 1980 src = fetchurl {
1976 url = "https://files.pythonhosted.org/packages/27/da/337fabeb3dca6b62039a93ceaa636f25065e0ae92b575b1235342076cf0a/sshpubkeys-2.2.0.tar.gz";
1977 sha256 = "0r4kpwzmg96a2x56pllik7dmc3fnqk189v3sfgsi07q2ryrhr6xm";
1981 url = "https://files.pythonhosted.org/packages/00/23/f7508a12007c96861c3da811992f14283d79c819d71a217b3e12d5196649/sshpubkeys-3.1.0.tar.gz";
1982 sha256 = "105g2li04nm1hb15a2y6hm9m9k7fbrkd5l3gy12w3kgcmsf3k25k";
1978 1983 };
1979 1984 meta = {
1980 1985 license = [ pkgs.lib.licenses.bsdOriginal ];
1981 1986 };
1982 1987 };
1983 1988 "subprocess32" = super.buildPythonPackage {
1984 name = "subprocess32-3.5.3";
1989 name = "subprocess32-3.5.4";
1985 1990 doCheck = false;
1986 1991 src = fetchurl {
1987 url = "https://files.pythonhosted.org/packages/be/2b/beeba583e9877e64db10b52a96915afc0feabf7144dcbf2a0d0ea68bf73d/subprocess32-3.5.3.tar.gz";
1988 sha256 = "1hr5fan8i719hmlmz73hf8rhq74014w07d8ryg7krvvf6692kj3b";
1992 url = "https://files.pythonhosted.org/packages/32/c8/564be4d12629b912ea431f1a50eb8b3b9d00f1a0b1ceff17f266be190007/subprocess32-3.5.4.tar.gz";
1993 sha256 = "17f7mvwx2271s1wrl0qac3wjqqnrqag866zs3qc8v5wp0k43fagb";
1989 1994 };
1990 1995 meta = {
1991 1996 license = [ pkgs.lib.licenses.psfl ];
1992 1997 };
1993 1998 };
1994 1999 "supervisor" = super.buildPythonPackage {
1995 name = "supervisor-3.3.5";
2000 name = "supervisor-4.0.3";
1996 2001 doCheck = false;
1997 2002 propagatedBuildInputs = [
1998 2003 self."meld3"
1999 2004 ];
2000 2005 src = fetchurl {
2001 url = "https://files.pythonhosted.org/packages/ba/65/92575a8757ed576beaee59251f64a3287bde82bdc03964b89df9e1d29e1b/supervisor-3.3.5.tar.gz";
2002 sha256 = "1w3ahridzbc6rxfpbyx8lij6pjlcgf2ymzyg53llkjqxalp6sk8v";
2006 url = "https://files.pythonhosted.org/packages/97/48/f38bf70bd9282d1a18d591616557cc1a77a1c627d57dff66ead65c891dc8/supervisor-4.0.3.tar.gz";
2007 sha256 = "17hla7mx6w5m5jzkkjxgqa8wpswqmfhbhf49f692hw78fg0ans7p";
2003 2008 };
2004 2009 meta = {
2005 2010 license = [ { fullName = "BSD-derived (http://www.repoze.org/LICENSE.txt)"; } ];
@@ -2128,22 +2133,22 b' self: super: {'
2128 2133 };
2129 2134 };
2130 2135 "vine" = super.buildPythonPackage {
2131 name = "vine-1.2.0";
2136 name = "vine-1.3.0";
2132 2137 doCheck = false;
2133 2138 src = fetchurl {
2134 url = "https://files.pythonhosted.org/packages/46/1a/c94317efa98040c5d50fe3cf9080cafb0372ff5afb0283dc018c751c6746/vine-1.2.0.tar.gz";
2135 sha256 = "0xjz2sjbr5jrpjk411b7alkghdskhphgsqqrbi7abqfh2pli6j7f";
2139 url = "https://files.pythonhosted.org/packages/1c/e1/79fb8046e607dd6c2ad05c9b8ebac9d0bd31d086a08f02699e96fc5b3046/vine-1.3.0.tar.gz";
2140 sha256 = "11ydsbhl1vabndc2r979dv61s6j2b0giq6dgvryifvq1m7bycghk";
2136 2141 };
2137 2142 meta = {
2138 2143 license = [ pkgs.lib.licenses.bsdOriginal ];
2139 2144 };
2140 2145 };
2141 2146 "waitress" = super.buildPythonPackage {
2142 name = "waitress-1.1.0";
2147 name = "waitress-1.3.0";
2143 2148 doCheck = false;
2144 2149 src = fetchurl {
2145 url = "https://files.pythonhosted.org/packages/3c/68/1c10dd5c556872ceebe88483b0436140048d39de83a84a06a8baa8136f4f/waitress-1.1.0.tar.gz";
2146 sha256 = "1a85gyji0kajc3p0s1pwwfm06w4wfxjkvvl4rnrz3h164kbd6g6k";
2150 url = "https://files.pythonhosted.org/packages/43/50/9890471320d5ad22761ae46661cf745f487b1c8c4ec49352b99e1078b970/waitress-1.3.0.tar.gz";
2151 sha256 = "09j5dzbbcxib7vdskhx39s1qsydlr4n2p2png71d7mjnr9pnwajf";
2147 2152 };
2148 2153 meta = {
2149 2154 license = [ pkgs.lib.licenses.zpl21 ];
@@ -2218,18 +2223,18 b' self: super: {'
2218 2223 };
2219 2224 };
2220 2225 "webob" = super.buildPythonPackage {
2221 name = "webob-1.8.4";
2226 name = "webob-1.8.5";
2222 2227 doCheck = false;
2223 2228 src = fetchurl {
2224 url = "https://files.pythonhosted.org/packages/e4/6c/99e322c3d4cc11d9060a67a9bf2f7c9c581f40988c11fffe89bb8c36bc5e/WebOb-1.8.4.tar.gz";
2225 sha256 = "16cfg5y4n6sihz59vsmns2yqbfm0gfsn3l5xgz2g0pdhilaib0x4";
2229 url = "https://files.pythonhosted.org/packages/9d/1a/0c89c070ee2829c934cb6c7082287c822e28236a4fcf90063e6be7c35532/WebOb-1.8.5.tar.gz";
2230 sha256 = "11khpzaxc88q31v25ic330gsf56fwmbdc9b30br8mvp0fmwspah5";
2226 2231 };
2227 2232 meta = {
2228 2233 license = [ pkgs.lib.licenses.mit ];
2229 2234 };
2230 2235 };
2231 2236 "webtest" = super.buildPythonPackage {
2232 name = "webtest-2.0.32";
2237 name = "webtest-2.0.33";
2233 2238 doCheck = false;
2234 2239 propagatedBuildInputs = [
2235 2240 self."six"
@@ -2238,8 +2243,8 b' self: super: {'
2238 2243 self."beautifulsoup4"
2239 2244 ];
2240 2245 src = fetchurl {
2241 url = "https://files.pythonhosted.org/packages/27/9f/9e74449d272ffbef4fb3012e6dbc53c0b24822d545e7a33a342f80131e59/WebTest-2.0.32.tar.gz";
2242 sha256 = "0qp0nnbazzm4ibjiyqfcn6f230svk09i4g58zg2i9x1ga06h48a2";
2246 url = "https://files.pythonhosted.org/packages/a8/b0/ffc9413b637dbe26e291429bb0f6ed731e518d0cd03da28524a8fe2e8a8f/WebTest-2.0.33.tar.gz";
2247 sha256 = "1l3z0cwqslsf4rcrhi2gr8kdfh74wn2dw76376i4g9i38gz8wd21";
2243 2248 };
2244 2249 meta = {
2245 2250 license = [ pkgs.lib.licenses.mit ];
@@ -2293,42 +2298,42 b' self: super: {'
2293 2298 };
2294 2299 };
2295 2300 "zope.deprecation" = super.buildPythonPackage {
2296 name = "zope.deprecation-4.3.0";
2301 name = "zope.deprecation-4.4.0";
2297 2302 doCheck = false;
2298 2303 propagatedBuildInputs = [
2299 2304 self."setuptools"
2300 2305 ];
2301 2306 src = fetchurl {
2302 url = "https://files.pythonhosted.org/packages/a1/18/2dc5e6bfe64fdc3b79411b67464c55bb0b43b127051a20f7f492ab767758/zope.deprecation-4.3.0.tar.gz";
2303 sha256 = "095jas41wbxgmw95kwdxqhbc3bgihw2hzj9b3qpdg85apcsf2lkx";
2307 url = "https://files.pythonhosted.org/packages/34/da/46e92d32d545dd067b9436279d84c339e8b16de2ca393d7b892bc1e1e9fd/zope.deprecation-4.4.0.tar.gz";
2308 sha256 = "1pz2cv7gv9y1r3m0bdv7ks1alagmrn5msm5spwdzkb2by0w36i8d";
2304 2309 };
2305 2310 meta = {
2306 2311 license = [ pkgs.lib.licenses.zpl21 ];
2307 2312 };
2308 2313 };
2309 2314 "zope.event" = super.buildPythonPackage {
2310 name = "zope.event-4.3.0";
2315 name = "zope.event-4.4";
2311 2316 doCheck = false;
2312 2317 propagatedBuildInputs = [
2313 2318 self."setuptools"
2314 2319 ];
2315 2320 src = fetchurl {
2316 url = "https://files.pythonhosted.org/packages/9e/d0/54ba59f19a0635f6591b74be259cf6fbf67e73f4edda27b5cd0cf4d26efa/zope.event-4.3.0.tar.gz";
2317 sha256 = "1rrkyx42bcq8dkpj23c2v99kczlrg8d39c06q5qpr0vs4hjfmv70";
2321 url = "https://files.pythonhosted.org/packages/4c/b2/51c0369adcf5be2334280eed230192ab3b03f81f8efda9ddea6f65cc7b32/zope.event-4.4.tar.gz";
2322 sha256 = "1ksbc726av9xacml6jhcfyn828hlhb9xlddpx6fcvnlvmpmpvhk9";
2318 2323 };
2319 2324 meta = {
2320 2325 license = [ pkgs.lib.licenses.zpl21 ];
2321 2326 };
2322 2327 };
2323 2328 "zope.interface" = super.buildPythonPackage {
2324 name = "zope.interface-4.5.0";
2329 name = "zope.interface-4.6.0";
2325 2330 doCheck = false;
2326 2331 propagatedBuildInputs = [
2327 2332 self."setuptools"
2328 2333 ];
2329 2334 src = fetchurl {
2330 url = "https://files.pythonhosted.org/packages/ac/8a/657532df378c2cd2a1fe6b12be3b4097521570769d4852ec02c24bd3594e/zope.interface-4.5.0.tar.gz";
2331 sha256 = "0k67m60ij06wkg82n15qgyn96waf4pmrkhv0njpkfzpmv5q89hsp";
2335 url = "https://files.pythonhosted.org/packages/4e/d0/c9d16bd5b38de44a20c6dc5d5ed80a49626fafcb3db9f9efdc2a19026db6/zope.interface-4.6.0.tar.gz";
2336 sha256 = "1rgh2x3rcl9r0v0499kf78xy86rnmanajf4ywmqb943wpk50sg8v";
2332 2337 };
2333 2338 meta = {
2334 2339 license = [ pkgs.lib.licenses.zpl21 ];
@@ -1,37 +1,31 b''
1 1 ## dependencies
2 2
3 setuptools-scm==2.1.0
4 3 amqp==2.3.1
5 4 # not released authomatic that has updated some oauth providers
6 https://code.rhodecode.com/upstream/authomatic/archive/90a9ce60cc405ae8a2bf5c3713acd5d78579a04e.tar.gz?md5=3c68720a1322b25254009518d1ff6801#egg=authomatic==0.1.0.post1
7 atomicwrites==1.2.1
8 attrs==18.2.0
5 https://code.rhodecode.com/upstream/authomatic/artifacts/download/0-4fe9c041-a567-4f84-be4c-7efa2a606d3c.tar.gz?md5=f6bdc3c769688212db68233e8d2b0383#egg=authomatic==0.1.0.post1
6
9 7 babel==1.3
10 8 beaker==1.9.1
11 bleach==3.0.2
9 bleach==3.1.0
12 10 celery==4.1.1
13 chameleon==2.24
14 11 channelstream==0.5.2
15 12 click==7.0
16 colander==1.5.1
13 colander==1.7.0
17 14 # our custom configobj
18 https://code.rhodecode.com/upstream/configobj/archive/a11ff0a0bd4fbda9e3a91267e720f88329efb4a6.tar.gz?md5=9916c524ea11a6c418217af6b28d4b3c#egg=configobj==5.0.6
15 https://code.rhodecode.com/upstream/configobj/artifacts/download/0-012de99a-b1e1-4f64-a5c0-07a98a41b324.tar.gz?md5=6a513f51fe04b2c18cf84c1395a7c626#egg=configobj==5.0.6
19 16 cssselect==1.0.3
17 cryptography==2.6.1
20 18 decorator==4.1.2
21 19 deform==2.0.7
22 20 docutils==0.14.0
23 21 dogpile.cache==0.7.1
24 22 dogpile.core==0.4.1
25 ecdsa==0.13
26 23 formencode==1.2.4
27 24 future==0.14.3
28 25 futures==3.0.2
29 gnureadline==6.3.8
30 26 infrae.cache==1.0.1
31 27 iso8601==0.1.12
32 28 itsdangerous==0.24
33 jinja2==2.9.6
34 billiard==3.5.0.3
35 29 kombu==4.2.1
36 30 lxml==4.2.5
37 31 mako==1.0.7
@@ -40,23 +34,20 b' markupsafe==1.1.0'
40 34 msgpack-python==0.5.6
41 35 pyotp==2.2.7
42 36 packaging==15.2
43 paste==3.0.5
37 pathlib2==2.3.4
38 paste==3.0.8
44 39 pastedeploy==2.0.1
45 pastescript==3.0.0
46 pathlib2==2.3.3
40 pastescript==3.1.0
47 41 peppercorn==0.6
48 psutil==5.4.8
42 psutil==5.5.1
49 43 py-bcrypt==0.4
50 pycrypto==2.6.1
51 44 pycurl==7.43.0.2
52 pyflakes==0.8.1
53 pygments==2.3.1
45 pycrypto==2.6.1
46 pygments==2.4.2
54 47 pyparsing==2.3.0
55 pyramid-beaker==0.8
56 48 pyramid-debugtoolbar==4.5.0
57 pyramid-jinja2==2.7
58 49 pyramid-mako==1.0.2
59 pyramid==1.10.1
50 pyramid==1.10.4
60 51 pyramid_mailer==0.15.1
61 52 python-dateutil
62 53 python-ldap==3.1.0
@@ -74,10 +65,9 b' routes==2.4.1'
74 65 simplejson==3.16.0
75 66 six==1.11.0
76 67 sqlalchemy==1.1.18
77 sshpubkeys==2.2.0
78 subprocess32==3.5.3
79 supervisor==3.3.5
80 tempita==0.5.2
68 sshpubkeys==3.1.0
69 subprocess32==3.5.4
70 supervisor==4.0.3
81 71 translationstring==1.3
82 72 urllib3==1.24.1
83 73 urlobject==2.4.3
@@ -85,29 +75,29 b' venusian==1.2.0'
85 75 weberror==0.10.3
86 76 webhelpers2==2.0
87 77 webhelpers==1.3
88 webob==1.8.4
78 webob==1.8.5
89 79 whoosh==2.7.4
90 80 wsgiref==0.1.2
91 81 zope.cachedescriptors==4.3.1
92 zope.deprecation==4.3.0
93 zope.event==4.3.0
94 zope.interface==4.5.0
82 zope.deprecation==4.4.0
83 zope.event==4.4.0
84 zope.interface==4.6.0
95 85
96 86 # DB drivers
97 87 mysql-python==1.2.5
98 88 pymysql==0.8.1
99 89 pysqlite==2.8.3
100 psycopg2==2.7.5
90 psycopg2==2.8.3
101 91
102 92 # IPYTHON RENDERING
103 93 # entrypoints backport, pypi version doesn't support egg installs
104 https://code.rhodecode.com/upstream/entrypoints/archive/96e6d645684e1af3d7df5b5272f3fe85a546b233.tar.gz?md5=7db37771aea9ac9fefe093e5d6987313#egg=entrypoints==0.2.2.rhodecode-upstream1
94 https://code.rhodecode.com/upstream/entrypoints/artifacts/download/0-8e9ee9e4-c4db-409c-b07e-81568fd1832d.tar.gz?md5=3a027b8ff1d257b91fe257de6c43357d#egg=entrypoints==0.2.2.rhodecode-upstream1
105 95 nbconvert==5.3.1
106 96 nbformat==4.4.0
107 97 jupyter_client==5.0.0
108 98
109 99 ## cli tools
110 alembic==1.0.5
100 alembic==1.0.10
111 101 invoke==0.13.0
112 102 bumpversion==0.5.3
113 103
@@ -115,15 +105,14 b' bumpversion==0.5.3'
115 105 gevent==1.4.0
116 106 greenlet==0.4.15
117 107 gunicorn==19.9.0
118 waitress==1.1.0
119 setproctitle==1.1.10
108 waitress==1.3.0
120 109
121 110 ## debug
122 ipdb==0.11.0
111 ipdb==0.12.0
123 112 ipython==5.1.0
124 113
125 114 ## rhodecode-tools, special case
126 https://code.rhodecode.com/rhodecode-tools-ce/archive/v1.2.1.tar.gz?md5=25bc2f7de1da318e547236d3fb463d28#egg=rhodecode-tools==1.2.1
115 https://code.rhodecode.com/rhodecode-tools-ce/artifacts/download/0-10ac93f4-bb7d-4b97-baea-68110743dd5a.tar.gz?md5=962dc77c06aceee62282b98d33149661#egg=rhodecode-tools==1.2.1
127 116
128 117 ## appenlight
129 118 appenlight-client==0.6.26
@@ -10,7 +10,7 b' gprof2dot==2017.9.19'
10 10
11 11 mock==1.0.1
12 12 cov-core==1.15.0
13 coverage==4.5.1
13 coverage==4.5.3
14 14
15 webtest==2.0.32
15 webtest==2.0.33
16 16 beautifulsoup4==4.6.3
@@ -1,1 +1,1 b''
1 4.16.2 No newline at end of file
1 4.17.0 No newline at end of file
@@ -45,7 +45,7 b' PYRAMID_SETTINGS = {}'
45 45 EXTENSIONS = {}
46 46
47 47 __version__ = ('.'.join((str(each) for each in VERSION[:3])))
48 __dbversion__ = 95 # defines current db version for migrations
48 __dbversion__ = 98 # defines current db version for migrations
49 49 __platform__ = platform.system()
50 50 __license__ = 'AGPLv3, and Commercial License'
51 51 __author__ = 'RhodeCode GmbH'
@@ -37,11 +37,11 b' class TestCommentCommit(object):'
37 37 assert_error(id_, expected, given=response.body)
38 38
39 39 @pytest.mark.parametrize("commit_id, expected_err", [
40 ('abcabca', {'hg': 'Commit {commit} does not exist for {repo}',
41 'git': 'Commit {commit} does not exist for {repo}',
40 ('abcabca', {'hg': 'Commit {commit} does not exist for `{repo}`',
41 'git': 'Commit {commit} does not exist for `{repo}`',
42 42 'svn': 'Commit id {commit} not understood.'}),
43 ('idontexist', {'hg': 'Commit {commit} does not exist for {repo}',
44 'git': 'Commit {commit} does not exist for {repo}',
43 ('idontexist', {'hg': 'Commit {commit} does not exist for `{repo}`',
44 'git': 'Commit {commit} does not exist for `{repo}`',
45 45 'svn': 'Commit id {commit} not understood.'}),
46 46 ])
47 47 def test_api_comment_commit_wrong_hash(self, backend, commit_id, expected_err):
@@ -53,7 +53,7 b' class TestCommentCommit(object):'
53 53
54 54 expected_err = expected_err[backend.alias]
55 55 expected_err = expected_err.format(
56 repo=backend.repo.scm_instance(), commit=commit_id)
56 repo=backend.repo.scm_instance().name, commit=commit_id)
57 57 assert_error(id_, expected_err, given=response.body)
58 58
59 59 @pytest.mark.parametrize("status_change, message, commit_id", [
@@ -44,6 +44,7 b' class TestGetRepo(object):'
44 44 self, apikey_attr, expect_secrets, cache_param, backend,
45 45 user_util):
46 46 repo = backend.create_repo()
47 repo_id = repo.repo_id
47 48 usr = UserModel().get_by_username(TEST_USER_ADMIN_LOGIN)
48 49 group = user_util.create_user_group(members=[usr])
49 50 user_util.grant_user_group_permission_to_repo(
@@ -64,6 +65,8 b' class TestGetRepo(object):'
64 65 permissions = expected_permissions(repo)
65 66
66 67 followers = []
68
69 repo = RepoModel().get(repo_id)
67 70 for user in repo.followers:
68 71 followers.append(user.user.get_api_data(
69 72 include_secrets=expect_secrets))
@@ -84,6 +87,7 b' class TestGetRepo(object):'
84 87 # TODO: Depending on which tests are running before this one, we
85 88 # start with a different number of permissions in the database.
86 89 repo = RepoModel().get_by_repo_name(backend.repo_name)
90 repo_id = repo.repo_id
87 91 permission_count = len(repo.repo_to_perm)
88 92
89 93 RepoModel().grant_user_permission(repo=backend.repo_name,
@@ -102,6 +106,8 b' class TestGetRepo(object):'
102 106 permissions = expected_permissions(repo)
103 107
104 108 followers = []
109
110 repo = RepoModel().get(repo_id)
105 111 for user in repo.followers:
106 112 followers.append(user.user.get_api_data())
107 113
@@ -444,7 +444,7 b' def get_repo_nodes(request, apiuser, rep'
444 444 result: [
445 445 {
446 446 "binary": false,
447 "content": "File line\nLine2\n",
447 "content": "File line",
448 448 "extension": "md",
449 449 "lines": 2,
450 450 "md5": "059fa5d29b19c0657e384749480f6422",
@@ -529,6 +529,7 b' def get_repo_file(request, apiuser, repo'
529 529 :param cache: Use internal caches for fetching files. If disabled fetching
530 530 files is slower but more memory efficient
531 531 :type cache: Optional(bool)
532
532 533 Example output:
533 534
534 535 .. code-block:: bash
@@ -168,6 +168,28 b' class BaseAppView(object):'
168 168 from rhodecode.lib.base import attach_context_attributes
169 169 attach_context_attributes(c, self.request, self.request.user.user_id)
170 170
171 c.is_super_admin = c.auth_user.is_admin
172
173 c.can_create_repo = c.is_super_admin
174 c.can_create_repo_group = c.is_super_admin
175 c.can_create_user_group = c.is_super_admin
176
177 c.is_delegated_admin = False
178
179 if not c.auth_user.is_default and not c.is_super_admin:
180 c.can_create_repo = h.HasPermissionAny('hg.create.repository')(
181 user=self.request.user)
182 repositories = c.auth_user.repositories_admin or c.can_create_repo
183
184 c.can_create_repo_group = h.HasPermissionAny('hg.repogroup.create.true')(
185 user=self.request.user)
186 repository_groups = c.auth_user.repository_groups_admin or c.can_create_repo_group
187
188 c.can_create_user_group = h.HasPermissionAny('hg.usergroup.create.true')(
189 user=self.request.user)
190 user_groups = c.auth_user.user_groups_admin or c.can_create_user_group
191 # delegated admin can create, or manage some objects
192 c.is_delegated_admin = repositories or repository_groups or user_groups
171 193 return c
172 194
173 195 def _get_template_context(self, tmpl_args, **kwargs):
@@ -215,12 +237,17 b' class RepoAppView(BaseAppView):'
215 237 c.rhodecode_db_repo = self.db_repo
216 238 c.repo_name = self.db_repo_name
217 239 c.repository_pull_requests = self.db_repo_pull_requests
240 c.repository_is_user_following = ScmModel().is_following_repo(
241 self.db_repo_name, self._rhodecode_user.user_id)
218 242 self.path_filter = PathFilter(None)
219 243
220 244 c.repository_requirements_missing = {}
221 245 try:
222 246 self.rhodecode_vcs_repo = self.db_repo.scm_instance()
223 if self.rhodecode_vcs_repo:
247 # NOTE(marcink):
248 # comparison to None since if it's an object __bool__ is expensive to
249 # calculate
250 if self.rhodecode_vcs_repo is not None:
224 251 path_perms = self.rhodecode_vcs_repo.get_path_permissions(
225 252 c.auth_user.username)
226 253 self.path_filter = PathFilter(path_perms)
@@ -85,8 +85,6 b' class NavigationRegistry(object):'
85 85 'admin_settings_hooks'),
86 86 NavEntry('search', _('Full Text Search'),
87 87 'admin_settings_search'),
88 NavEntry('integrations', _('Integrations'),
89 'global_integrations_home'),
90 88 NavEntry('system', _('System Info'),
91 89 'admin_settings_system'),
92 90 NavEntry('exceptions', _('Exceptions Tracker'),
@@ -424,6 +424,10 b' def admin_routes(config):'
424 424 pattern='/repo_groups')
425 425
426 426 config.add_route(
427 name='repo_groups_data',
428 pattern='/repo_groups_data')
429
430 config.add_route(
427 431 name='repo_group_new',
428 432 pattern='/repo_group/new')
429 433
@@ -46,10 +46,10 b' def route_path(name, params=None, **kwar'
46 46
47 47 class TestAdminMainView(TestController):
48 48
49 def test_redirect_admin_home(self):
49 def test_access_admin_home(self):
50 50 self.log_user()
51 response = self.app.get(route_path('admin_home'), status=302)
52 assert response.location.endswith('/audit_logs')
51 response = self.app.get(route_path('admin_home'), status=200)
52 response.mustcontain("Administration area")
53 53
54 54 def test_redirect_pull_request_view(self, view):
55 55 self.log_user()
@@ -23,11 +23,11 b' import pytest'
23 23
24 24 from rhodecode.apps._base import ADMIN_PREFIX
25 25 from rhodecode.lib import helpers as h
26 from rhodecode.model.db import Repository, UserRepoToPerm, User
26 from rhodecode.model.db import Repository, UserRepoToPerm, User, RepoGroup
27 27 from rhodecode.model.meta import Session
28 28 from rhodecode.model.repo_group import RepoGroupModel
29 29 from rhodecode.tests import (
30 assert_session_flash, TEST_USER_REGULAR_LOGIN, TESTS_TMP_PATH, TestController)
30 assert_session_flash, TEST_USER_REGULAR_LOGIN, TESTS_TMP_PATH)
31 31 from rhodecode.tests.fixture import Fixture
32 32
33 33 fixture = Fixture()
@@ -38,6 +38,7 b' def route_path(name, params=None, **kwar'
38 38
39 39 base_url = {
40 40 'repo_groups': ADMIN_PREFIX + '/repo_groups',
41 'repo_groups_data': ADMIN_PREFIX + '/repo_groups_data',
41 42 'repo_group_new': ADMIN_PREFIX + '/repo_group/new',
42 43 'repo_group_create': ADMIN_PREFIX + '/repo_group/create',
43 44
@@ -59,13 +60,30 b' def _get_permission_for_user(user, repo)'
59 60
60 61 @pytest.mark.usefixtures("app")
61 62 class TestAdminRepositoryGroups(object):
63
62 64 def test_show_repo_groups(self, autologin_user):
63 response = self.app.get(route_path('repo_groups'))
64 response.mustcontain('data: []')
65 self.app.get(route_path('repo_groups'))
66
67 def test_show_repo_groups_data(self, autologin_user, xhr_header):
68 response = self.app.get(route_path(
69 'repo_groups_data'), extra_environ=xhr_header)
70
71 all_repo_groups = RepoGroup.query().count()
72 assert response.json['recordsTotal'] == all_repo_groups
65 73
66 def test_show_repo_groups_after_creating_group(self, autologin_user):
74 def test_show_repo_groups_data_filtered(self, autologin_user, xhr_header):
75 response = self.app.get(route_path(
76 'repo_groups_data', params={'search[value]': 'empty_search'}),
77 extra_environ=xhr_header)
78
79 all_repo_groups = RepoGroup.query().count()
80 assert response.json['recordsTotal'] == all_repo_groups
81 assert response.json['recordsFiltered'] == 0
82
83 def test_show_repo_groups_after_creating_group(self, autologin_user, xhr_header):
67 84 fixture.create_repo_group('test_repo_group')
68 response = self.app.get(route_path('repo_groups'))
85 response = self.app.get(route_path(
86 'repo_groups_data'), extra_environ=xhr_header)
69 87 response.mustcontain('"name_raw": "test_repo_group"')
70 88 fixture.destroy_repo_group('test_repo_group')
71 89
@@ -214,8 +214,7 b' class TestAdminSettingsGlobal(object):'
214 214 })
215 215
216 216 response = response.follow()
217 response.mustcontain(
218 """<div class="branding">- %s</div>""" % new_title)
217 response.mustcontain(new_title)
219 218
220 219 def post_and_verify_settings(self, settings):
221 220 old_title = 'RhodeCode'
@@ -173,4 +173,4 b' class TestAdminUsersSshKeysView(TestCont'
173 173
174 174 response.mustcontain('Private key')
175 175 response.mustcontain('Public key')
176 response.mustcontain('-----BEGIN RSA PRIVATE KEY-----')
176 response.mustcontain('-----BEGIN PRIVATE KEY-----')
@@ -50,7 +50,7 b' class ExceptionsTrackerView(BaseAppView)'
50 50 count +=1
51 51 return count
52 52
53 def get_all_exceptions(self, read_metadata=False, limit=None):
53 def get_all_exceptions(self, read_metadata=False, limit=None, type_filter=None):
54 54 exc_store_path = exc_tracking.get_exc_store()
55 55 exception_list = []
56 56
@@ -59,7 +59,7 b' class ExceptionsTrackerView(BaseAppView)'
59 59 return val.split('_')[-1]
60 60 except Exception:
61 61 return 0
62 count = 0
62
63 63 for fname in reversed(sorted(os.listdir(exc_store_path), key=key_sorter)):
64 64
65 65 parts = fname.split('_', 2)
@@ -83,13 +83,17 b' class ExceptionsTrackerView(BaseAppView)'
83 83 except Exception:
84 84 log.exception('Failed to read exc data from:{}'.format(full_path))
85 85 pass
86
87 86 # convert our timestamp to a date obj, for nicer representation
88 87 exc['exc_utc_date'] = time_to_utcdatetime(exc['exc_timestamp'])
89 exception_list.append(exc)
90 88
91 count += 1
92 if limit and count >= limit:
89 type_present = exc.get('exc_type')
90 if type_filter:
91 if type_present and type_present == type_filter:
92 exception_list.append(exc)
93 else:
94 exception_list.append(exc)
95
96 if limit and len(exception_list) >= limit:
93 97 break
94 98 return exception_list
95 99
@@ -103,8 +107,10 b' class ExceptionsTrackerView(BaseAppView)'
103 107 c = self.load_default_context()
104 108 c.active = 'exceptions_browse'
105 109 c.limit = safe_int(self.request.GET.get('limit')) or 50
110 c.type_filter = self.request.GET.get('type_filter')
106 111 c.next_limit = c.limit + 50
107 c.exception_list = self.get_all_exceptions(read_metadata=True, limit=c.limit)
112 c.exception_list = self.get_all_exceptions(
113 read_metadata=True, limit=c.limit, type_filter=c.type_filter)
108 114 c.exception_list_count = self.count_all_exceptions()
109 115 c.exception_store_dir = exc_tracking.get_exc_store()
110 116 return self._get_template_context(c)
@@ -132,12 +138,20 b' class ExceptionsTrackerView(BaseAppView)'
132 138 def exception_delete_all(self):
133 139 _ = self.request.translate
134 140 c = self.load_default_context()
141 type_filter = self.request.POST.get('type_filter')
135 142
136 143 c.active = 'exceptions'
137 all_exc = self.get_all_exceptions()
138 exc_count = len(all_exc)
144 all_exc = self.get_all_exceptions(read_metadata=bool(type_filter), type_filter=type_filter)
145 exc_count = 0
146
139 147 for exc in all_exc:
140 exc_tracking.delete_exception(exc['exc_id'], prefix=None)
148 if type_filter:
149 if exc.get('exc_type') == type_filter:
150 exc_tracking.delete_exception(exc['exc_id'], prefix=None)
151 exc_count += 1
152 else:
153 exc_tracking.delete_exception(exc['exc_id'], prefix=None)
154 exc_count += 1
141 155
142 156 h.flash(_('Removed {} Exceptions').format(exc_count), category='success')
143 157 raise HTTPFound(h.route_path('admin_settings_exception_tracker'))
@@ -20,12 +20,12 b''
20 20
21 21 import logging
22 22
23 from pyramid.httpexceptions import HTTPFound
23 from pyramid.httpexceptions import HTTPFound, HTTPNotFound
24 24 from pyramid.view import view_config
25 25
26 26 from rhodecode.apps._base import BaseAppView
27 27 from rhodecode.lib import helpers as h
28 from rhodecode.lib.auth import (LoginRequired, HasPermissionAllDecorator)
28 from rhodecode.lib.auth import (LoginRequired, NotAnonymous)
29 29 from rhodecode.model.db import PullRequest
30 30
31 31
@@ -33,14 +33,23 b' log = logging.getLogger(__name__)'
33 33
34 34
35 35 class AdminMainView(BaseAppView):
36 def load_default_context(self):
37 c = self._get_local_tmpl_context()
38 return c
36 39
37 40 @LoginRequired()
38 @HasPermissionAllDecorator('hg.admin')
41 @NotAnonymous()
39 42 @view_config(
40 route_name='admin_home', request_method='GET')
43 route_name='admin_home', request_method='GET',
44 renderer='rhodecode:templates/admin/main.mako')
41 45 def admin_main(self):
42 # redirect _admin to audit logs...
43 raise HTTPFound(h.route_path('admin_audit_logs'))
46 c = self.load_default_context()
47 c.active = 'admin'
48
49 if not (c.is_super_admin or c.is_delegated_admin):
50 raise HTTPNotFound()
51
52 return self._get_template_context(c)
44 53
45 54 @LoginRequired()
46 55 @view_config(route_name='pull_requests_global_0', request_method='GET')
@@ -49,8 +58,7 b' class AdminMainView(BaseAppView):'
49 58 def pull_requests(self):
50 59 """
51 60 Global redirect for Pull Requests
52
53 :param pull_request_id: id of pull requests in the system
61 pull_request_id: id of pull requests in the system
54 62 """
55 63
56 64 pull_request = PullRequest.get_or_404(
@@ -17,7 +17,7 b''
17 17 # This program is dual-licensed. If you wish to learn more about the
18 18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20
20 import datetime
21 21 import logging
22 22 import formencode
23 23 import formencode.htmlfill
@@ -30,16 +30,16 b' from pyramid.response import Response'
30 30 from rhodecode import events
31 31 from rhodecode.apps._base import BaseAppView, DataGridAppView
32 32
33 from rhodecode.lib.ext_json import json
34 33 from rhodecode.lib.auth import (
35 34 LoginRequired, CSRFRequired, NotAnonymous,
36 35 HasPermissionAny, HasRepoGroupPermissionAny)
37 36 from rhodecode.lib import helpers as h, audit_logger
38 from rhodecode.lib.utils2 import safe_int, safe_unicode
37 from rhodecode.lib.utils2 import safe_int, safe_unicode, datetime_to_time
39 38 from rhodecode.model.forms import RepoGroupForm
40 39 from rhodecode.model.repo_group import RepoGroupModel
41 40 from rhodecode.model.scm import RepoGroupList
42 from rhodecode.model.db import Session, RepoGroup
41 from rhodecode.model.db import (
42 or_, count, func, in_filter_generator, Session, RepoGroup, User, Repository)
43 43
44 44 log = logging.getLogger(__name__)
45 45
@@ -88,22 +88,168 b' class AdminRepoGroupsView(BaseAppView, D'
88 88 return False
89 89 return False
90 90
91 # permission check in data loading of
92 # `repo_group_list_data` via RepoGroupList
91 93 @LoginRequired()
92 94 @NotAnonymous()
93 # perms check inside
94 95 @view_config(
95 96 route_name='repo_groups', request_method='GET',
96 97 renderer='rhodecode:templates/admin/repo_groups/repo_groups.mako')
97 98 def repo_group_list(self):
98 99 c = self.load_default_context()
100 return self._get_template_context(c)
99 101
100 repo_group_list = RepoGroup.get_all_repo_groups()
101 repo_group_list_acl = RepoGroupList(
102 repo_group_list, perm_set=['group.admin'])
103 repo_group_data = RepoGroupModel().get_repo_groups_as_dict(
104 repo_group_list=repo_group_list_acl, admin=True)
105 c.data = json.dumps(repo_group_data)
106 return self._get_template_context(c)
102 # permission check inside
103 @LoginRequired()
104 @NotAnonymous()
105 @view_config(
106 route_name='repo_groups_data', request_method='GET',
107 renderer='json_ext', xhr=True)
108 def repo_group_list_data(self):
109 self.load_default_context()
110 column_map = {
111 'name_raw': 'group_name_hash',
112 'desc': 'group_description',
113 'last_change_raw': 'updated_on',
114 'top_level_repos': 'repos_total',
115 'owner': 'user_username',
116 }
117 draw, start, limit = self._extract_chunk(self.request)
118 search_q, order_by, order_dir = self._extract_ordering(
119 self.request, column_map=column_map)
120
121 _render = self.request.get_partial_renderer(
122 'rhodecode:templates/data_table/_dt_elements.mako')
123 c = _render.get_call_context()
124
125 def quick_menu(repo_group_name):
126 return _render('quick_repo_group_menu', repo_group_name)
127
128 def repo_group_lnk(repo_group_name):
129 return _render('repo_group_name', repo_group_name)
130
131 def last_change(last_change):
132 if isinstance(last_change, datetime.datetime) and not last_change.tzinfo:
133 delta = datetime.timedelta(
134 seconds=(datetime.datetime.now() - datetime.datetime.utcnow()).seconds)
135 last_change = last_change + delta
136 return _render("last_change", last_change)
137
138 def desc(desc, personal):
139 return _render(
140 'repo_group_desc', desc, personal, c.visual.stylify_metatags)
141
142 def repo_group_actions(repo_group_id, repo_group_name, gr_count):
143 return _render(
144 'repo_group_actions', repo_group_id, repo_group_name, gr_count)
145
146 def user_profile(username):
147 return _render('user_profile', username)
148
149 auth_repo_group_list = RepoGroupList(
150 RepoGroup.query().all(), perm_set=['group.admin'])
151
152 allowed_ids = [-1]
153 for repo_group in auth_repo_group_list:
154 allowed_ids.append(repo_group.group_id)
155
156 repo_groups_data_total_count = RepoGroup.query()\
157 .filter(or_(
158 # generate multiple IN to fix limitation problems
159 *in_filter_generator(RepoGroup.group_id, allowed_ids)
160 )) \
161 .count()
162
163 repo_groups_data_total_inactive_count = RepoGroup.query()\
164 .filter(RepoGroup.group_id.in_(allowed_ids))\
165 .count()
166
167 repo_count = count(Repository.repo_id)
168 base_q = Session.query(
169 RepoGroup.group_name,
170 RepoGroup.group_name_hash,
171 RepoGroup.group_description,
172 RepoGroup.group_id,
173 RepoGroup.personal,
174 RepoGroup.updated_on,
175 User,
176 repo_count.label('repos_count')
177 ) \
178 .filter(or_(
179 # generate multiple IN to fix limitation problems
180 *in_filter_generator(RepoGroup.group_id, allowed_ids)
181 )) \
182 .outerjoin(Repository) \
183 .join(User, User.user_id == RepoGroup.user_id) \
184 .group_by(RepoGroup, User)
185
186 if search_q:
187 like_expression = u'%{}%'.format(safe_unicode(search_q))
188 base_q = base_q.filter(or_(
189 RepoGroup.group_name.ilike(like_expression),
190 ))
191
192 repo_groups_data_total_filtered_count = base_q.count()
193 # the inactive isn't really used, but we still make it same as other data grids
194 # which use inactive (users,user groups)
195 repo_groups_data_total_filtered_inactive_count = repo_groups_data_total_filtered_count
196
197 sort_defined = False
198 if order_by == 'group_name':
199 sort_col = func.lower(RepoGroup.group_name)
200 sort_defined = True
201 elif order_by == 'repos_total':
202 sort_col = repo_count
203 sort_defined = True
204 elif order_by == 'user_username':
205 sort_col = User.username
206 else:
207 sort_col = getattr(RepoGroup, order_by, None)
208
209 if sort_defined or sort_col:
210 if order_dir == 'asc':
211 sort_col = sort_col.asc()
212 else:
213 sort_col = sort_col.desc()
214
215 base_q = base_q.order_by(sort_col)
216 base_q = base_q.offset(start).limit(limit)
217
218 # authenticated access to user groups
219 auth_repo_group_list = base_q.all()
220
221 repo_groups_data = []
222 for repo_gr in auth_repo_group_list:
223 row = {
224 "menu": quick_menu(repo_gr.group_name),
225 "name": repo_group_lnk(repo_gr.group_name),
226 "name_raw": repo_gr.group_name,
227 "last_change": last_change(repo_gr.updated_on),
228 "last_change_raw": datetime_to_time(repo_gr.updated_on),
229
230 "last_changeset": "",
231 "last_changeset_raw": "",
232
233 "desc": desc(repo_gr.group_description, repo_gr.personal),
234 "owner": user_profile(repo_gr.User.username),
235 "top_level_repos": repo_gr.repos_count,
236 "action": repo_group_actions(
237 repo_gr.group_id, repo_gr.group_name, repo_gr.repos_count),
238
239 }
240
241 repo_groups_data.append(row)
242
243 data = ({
244 'draw': draw,
245 'data': repo_groups_data,
246 'recordsTotal': repo_groups_data_total_count,
247 'recordsTotalInactive': repo_groups_data_total_inactive_count,
248 'recordsFiltered': repo_groups_data_total_filtered_count,
249 'recordsFilteredInactive': repo_groups_data_total_filtered_inactive_count,
250 })
251
252 return data
107 253
108 254 @LoginRequired()
109 255 @NotAnonymous()
@@ -39,7 +39,7 b' from rhodecode.model.forms import UserGr'
39 39 from rhodecode.model.permission import PermissionModel
40 40 from rhodecode.model.scm import UserGroupList
41 41 from rhodecode.model.db import (
42 or_, count, User, UserGroup, UserGroupMember)
42 or_, count, User, UserGroup, UserGroupMember, in_filter_generator)
43 43 from rhodecode.model.meta import Session
44 44 from rhodecode.model.user_group import UserGroupModel
45 45 from rhodecode.model.db import true
@@ -107,11 +107,17 b' class AdminUserGroupsView(BaseAppView, D'
107 107 allowed_ids.append(user_group.users_group_id)
108 108
109 109 user_groups_data_total_count = UserGroup.query()\
110 .filter(UserGroup.users_group_id.in_(allowed_ids))\
110 .filter(or_(
111 # generate multiple IN to fix limitation problems
112 *in_filter_generator(UserGroup.users_group_id, allowed_ids)
113 ))\
111 114 .count()
112 115
113 116 user_groups_data_total_inactive_count = UserGroup.query()\
114 .filter(UserGroup.users_group_id.in_(allowed_ids))\
117 .filter(or_(
118 # generate multiple IN to fix limitation problems
119 *in_filter_generator(UserGroup.users_group_id, allowed_ids)
120 ))\
115 121 .filter(UserGroup.users_group_active != true()).count()
116 122
117 123 member_count = count(UserGroupMember.user_id)
@@ -123,11 +129,14 b' class AdminUserGroupsView(BaseAppView, D'
123 129 UserGroup.group_data,
124 130 User,
125 131 member_count.label('member_count')
126 ) \
127 .filter(UserGroup.users_group_id.in_(allowed_ids)) \
128 .outerjoin(UserGroupMember) \
129 .join(User, User.user_id == UserGroup.user_id) \
130 .group_by(UserGroup, User)
132 ) \
133 .filter(or_(
134 # generate multiple IN to fix limitation problems
135 *in_filter_generator(UserGroup.users_group_id, allowed_ids)
136 )) \
137 .outerjoin(UserGroupMember) \
138 .join(User, User.user_id == UserGroup.user_id) \
139 .group_by(UserGroup, User)
131 140
132 141 base_q_inactive = base_q.filter(UserGroup.users_group_active != true())
133 142
@@ -141,14 +150,16 b' class AdminUserGroupsView(BaseAppView, D'
141 150 user_groups_data_total_filtered_count = base_q.count()
142 151 user_groups_data_total_filtered_inactive_count = base_q_inactive.count()
143 152
153 sort_defined = False
144 154 if order_by == 'members_total':
145 155 sort_col = member_count
156 sort_defined = True
146 157 elif order_by == 'user_username':
147 158 sort_col = User.username
148 159 else:
149 160 sort_col = getattr(UserGroup, order_by, None)
150 161
151 if isinstance(sort_col, count) or sort_col:
162 if sort_defined or sort_col:
152 163 if order_dir == 'asc':
153 164 sort_col = sort_col.asc()
154 165 else:
@@ -162,7 +173,7 b' class AdminUserGroupsView(BaseAppView, D'
162 173
163 174 user_groups_data = []
164 175 for user_gr in auth_user_group_list:
165 user_groups_data.append({
176 row = {
166 177 "users_group_name": user_group_name(user_gr.users_group_name),
167 178 "name_raw": h.escape(user_gr.users_group_name),
168 179 "description": h.escape(user_gr.user_group_description),
@@ -175,7 +186,8 b' class AdminUserGroupsView(BaseAppView, D'
175 186 "owner": user_profile(user_gr.User.username),
176 187 "action": user_group_actions(
177 188 user_gr.users_group_id, user_gr.users_group_name)
178 })
189 }
190 user_groups_data.append(row)
179 191
180 192 data = ({
181 193 'draw': draw,
@@ -682,8 +682,7 b' class UsersView(UserAppView):'
682 682 if personal_repo_group:
683 683 raise HTTPFound(h.route_path('user_edit_advanced', user_id=user_id))
684 684
685 personal_repo_group_name = RepoGroupModel().get_personal_group_name(
686 c.user)
685 personal_repo_group_name = RepoGroupModel().get_personal_group_name(c.user)
687 686 named_personal_group = RepoGroup.get_by_group_name(
688 687 personal_repo_group_name)
689 688 try:
@@ -38,19 +38,18 b' class LocalFileStorage(object):'
38 38 """
39 39 Resolves a unique name and the correct path. If a filename
40 40 for that path already exists then a numeric prefix with values > 0 will be
41 added, for example test.jpg -> test-1.jpg etc. initially file would have 0 prefix.
41 added, for example test.jpg -> 1-test.jpg etc. initially file would have 0 prefix.
42 42
43 43 :param name: base name of file
44 44 :param directory: absolute directory path
45 45 """
46 46
47 basename, ext = os.path.splitext(name)
48 47 counter = 0
49 48 while True:
50 name = '%s-%d%s' % (basename, counter, ext)
49 name = '%d-%s' % (counter, name)
51 50
52 51 # sub_store prefix to optimize disk usage, e.g some_path/ab/final_file
53 sub_store = cls._sub_store_from_filename(basename)
52 sub_store = cls._sub_store_from_filename(name)
54 53 sub_store_path = os.path.join(directory, sub_store)
55 54 if not os.path.exists(sub_store_path):
56 55 os.makedirs(sub_store_path)
@@ -209,3 +208,16 b' class LocalFileStorage(object):'
209 208 filename = os.path.join(directory, filename)
210 209
211 210 return filename, metadata
211
212 def get_metadata(self, filename):
213 """
214 Reads JSON stored metadata for a file
215
216 :param filename:
217 :return:
218 """
219 filename = self.store_path(filename)
220 filename_meta = filename + '.meta'
221
222 with open(filename_meta, "rb") as source_meta:
223 return json.loads(source_meta.read())
@@ -21,6 +21,7 b' import os'
21 21 import pytest
22 22
23 23 from rhodecode.lib.ext_json import json
24 from rhodecode.model.db import Session, FileStore
24 25 from rhodecode.tests import TestController
25 26 from rhodecode.apps.file_store import utils, config_keys
26 27
@@ -46,9 +47,12 b' class TestFileStoreViews(TestController)'
46 47 ('abcde-0.exe', "1234567", True),
47 48 ('abcde-0.jpg', "xxxxx", False),
48 49 ])
49 def test_get_files_from_store(self, fid, content, exists, tmpdir):
50 self.log_user()
50 def test_get_files_from_store(self, fid, content, exists, tmpdir, user_util):
51 user = self.log_user()
52 user_id = user['user_id']
53 repo_id = user_util.create_repo().repo_id
51 54 store_path = self.app._pyramid_settings[config_keys.store_path]
55 store_uid = fid
52 56
53 57 if exists:
54 58 status = 200
@@ -58,17 +62,28 b' class TestFileStoreViews(TestController)'
58 62 f.write(content)
59 63
60 64 with open(filesystem_file, 'rb') as f:
61 fid, metadata = store.save_file(f, fid, extra_metadata={'filename': fid})
65 store_uid, metadata = store.save_file(f, fid, extra_metadata={'filename': fid})
66
67 entry = FileStore.create(
68 file_uid=store_uid, filename=metadata["filename"],
69 file_hash=metadata["sha256"], file_size=metadata["size"],
70 file_display_name='file_display_name',
71 file_description='repo artifact `{}`'.format(metadata["filename"]),
72 check_acl=True, user_id=user_id,
73 scope_repo_id=repo_id
74 )
75 Session().add(entry)
76 Session().commit()
62 77
63 78 else:
64 79 status = 404
65 80
66 response = self.app.get(route_path('download_file', fid=fid), status=status)
81 response = self.app.get(route_path('download_file', fid=store_uid), status=status)
67 82
68 83 if exists:
69 84 assert response.text == content
70 file_store_path = os.path.dirname(store.resolve_name(fid, store_path)[1])
71 metadata_file = os.path.join(file_store_path, fid + '.meta')
85 file_store_path = os.path.dirname(store.resolve_name(store_uid, store_path)[1])
86 metadata_file = os.path.join(file_store_path, store_uid + '.meta')
72 87 assert os.path.exists(metadata_file)
73 88 with open(metadata_file, 'rb') as f:
74 89 json_data = json.loads(f.read())
@@ -19,9 +19,10 b''
19 19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20 20
21 21
22 import os
23 22 import uuid
24 23
24 import pathlib2
25
25 26
26 27 def get_file_storage(settings):
27 28 from rhodecode.apps.file_store.local_store import LocalFileStorage
@@ -30,6 +31,11 b' def get_file_storage(settings):'
30 31 return LocalFileStorage(base_path=store_path)
31 32
32 33
34 def splitext(filename):
35 ext = ''.join(pathlib2.Path(filename).suffixes)
36 return filename, ext
37
38
33 39 def uid_filename(filename, randomized=True):
34 40 """
35 41 Generates a randomized or stable (uuid) filename,
@@ -38,7 +44,8 b' def uid_filename(filename, randomized=Tr'
38 44 :param filename: the original filename
39 45 :param randomized: define if filename should be stable (sha1 based) or randomized
40 46 """
41 _, ext = os.path.splitext(filename)
47
48 _, ext = splitext(filename)
42 49 if randomized:
43 50 uid = uuid.uuid4()
44 51 else:
@@ -30,7 +30,7 b' from rhodecode.apps.file_store.exception'
30 30
31 31 from rhodecode.lib import helpers as h
32 32 from rhodecode.lib import audit_logger
33 from rhodecode.lib.auth import (CSRFRequired, NotAnonymous)
33 from rhodecode.lib.auth import (CSRFRequired, NotAnonymous, HasRepoPermissionAny, HasRepoGroupPermissionAny)
34 34 from rhodecode.model.db import Session, FileStore
35 35
36 36 log = logging.getLogger(__name__)
@@ -68,7 +68,7 b' class FileStoreView(BaseAppView):'
68 68 'user_id': self._rhodecode_user.user_id,
69 69 'ip': self._rhodecode_user.ip_addr}}
70 70 try:
71 store_fid, metadata = self.storage.save_file(
71 store_uid, metadata = self.storage.save_file(
72 72 file_obj.file, filename, extra_metadata=metadata)
73 73 except FileNotAllowedException:
74 74 return {'store_fid': None,
@@ -82,7 +82,7 b' class FileStoreView(BaseAppView):'
82 82
83 83 try:
84 84 entry = FileStore.create(
85 file_uid=store_fid, filename=metadata["filename"],
85 file_uid=store_uid, filename=metadata["filename"],
86 86 file_hash=metadata["sha256"], file_size=metadata["size"],
87 87 file_description='upload attachment',
88 88 check_acl=False, user_id=self._rhodecode_user.user_id
@@ -96,8 +96,8 b' class FileStoreView(BaseAppView):'
96 96 'access_path': None,
97 97 'error': 'File {} failed to store in DB.'.format(filename)}
98 98
99 return {'store_fid': store_fid,
100 'access_path': h.route_path('download_file', fid=store_fid)}
99 return {'store_fid': store_uid,
100 'access_path': h.route_path('download_file', fid=store_uid)}
101 101
102 102 @view_config(route_name='download_file')
103 103 def download_file(self):
@@ -109,6 +109,35 b' class FileStoreView(BaseAppView):'
109 109 log.debug('File with FID:%s not found in the store', file_uid)
110 110 raise HTTPNotFound()
111 111
112 db_obj = FileStore().query().filter(FileStore.file_uid == file_uid).scalar()
113 if not db_obj:
114 raise HTTPNotFound()
115
116 # private upload for user
117 if db_obj.check_acl and db_obj.scope_user_id:
118 user = db_obj.user
119 if self._rhodecode_db_user.user_id != user.user_id:
120 log.warning('Access to file store object forbidden')
121 raise HTTPNotFound()
122
123 # scoped to repository permissions
124 if db_obj.check_acl and db_obj.scope_repo_id:
125 repo = db_obj.repo
126 perm_set = ['repository.read', 'repository.write', 'repository.admin']
127 has_perm = HasRepoPermissionAny(*perm_set)(repo.repo_name, 'FileStore check')
128 if not has_perm:
129 log.warning('Access to file store object forbidden')
130 raise HTTPNotFound()
131
132 # scoped to repository group permissions
133 if db_obj.check_acl and db_obj.scope_repo_group_id:
134 repo_group = db_obj.repo_group
135 perm_set = ['group.read', 'group.write', 'group.admin']
136 has_perm = HasRepoGroupPermissionAny(*perm_set)(repo_group.group_name, 'FileStore check')
137 if not has_perm:
138 log.warning('Access to file store object forbidden')
139 raise HTTPNotFound()
140
112 141 FileStore.bump_access_counter(file_uid)
113 142
114 143 file_path = self.storage.store_path(file_uid)
@@ -25,7 +25,7 b' import formencode'
25 25 import formencode.htmlfill
26 26 import peppercorn
27 27
28 from pyramid.httpexceptions import HTTPNotFound, HTTPFound
28 from pyramid.httpexceptions import HTTPNotFound, HTTPFound, HTTPBadRequest
29 29 from pyramid.view import view_config
30 30 from pyramid.renderers import render
31 31 from pyramid.response import Response
@@ -67,7 +67,6 b' class GistView(BaseAppView):'
67 67 (Gist.ACL_LEVEL_PUBLIC, _("Can be accessed by anonymous users"))
68 68 ]
69 69
70
71 70 return c
72 71
73 72 @LoginRequired()
@@ -296,6 +295,8 b' class GistView(BaseAppView):'
296 295 response = Response(content)
297 296 response.content_type = 'text/plain'
298 297 return response
298 elif return_format:
299 raise HTTPBadRequest()
299 300
300 301 return self._get_template_context(c)
301 302
@@ -68,6 +68,10 b' def includeme(config):'
68 68 pattern='/_markup_preview')
69 69
70 70 config.add_route(
71 name='file_preview',
72 pattern='/_file_preview')
73
74 config.add_route(
71 75 name='store_user_session_value',
72 76 pattern='/_store_session_attr')
73 77
@@ -27,13 +27,14 b' from pyramid.view import view_config'
27 27 from rhodecode.apps._base import BaseAppView
28 28 from rhodecode.lib import helpers as h
29 29 from rhodecode.lib.auth import (
30 LoginRequired, NotAnonymous, HasRepoGroupPermissionAnyDecorator,
31 CSRFRequired)
30 LoginRequired, NotAnonymous, HasRepoGroupPermissionAnyDecorator, CSRFRequired)
31 from rhodecode.lib.codeblocks import filenode_as_lines_tokens
32 32 from rhodecode.lib.index import searcher_from_config
33 33 from rhodecode.lib.utils2 import safe_unicode, str2bool, safe_int
34 34 from rhodecode.lib.ext_json import json
35 from rhodecode.lib.vcs.nodes import FileNode
35 36 from rhodecode.model.db import (
36 func, true, or_, in_filter_generator, Repository, RepoGroup, User, UserGroup)
37 func, true, or_, case, in_filter_generator, Repository, RepoGroup, User, UserGroup)
37 38 from rhodecode.model.repo import RepoModel
38 39 from rhodecode.model.repo_group import RepoGroupModel
39 40 from rhodecode.model.scm import RepoGroupList, RepoList
@@ -105,21 +106,27 b' class HomeView(BaseAppView):'
105 106
106 107 return {'suggestions': _user_groups}
107 108
108 def _get_repo_list(self, name_contains=None, repo_type=None, limit=20):
109 def _get_repo_list(self, name_contains=None, repo_type=None, repo_group_name='', limit=20):
109 110 org_query = name_contains
110 111 allowed_ids = self._rhodecode_user.repo_acl_ids(
111 112 ['repository.read', 'repository.write', 'repository.admin'],
112 113 cache=False, name_filter=name_contains) or [-1]
113 114
114 115 query = Repository.query()\
115 .order_by(func.length(Repository.repo_name))\
116 .order_by(Repository.repo_name)\
117 116 .filter(Repository.archived.isnot(true()))\
118 117 .filter(or_(
119 118 # generate multiple IN to fix limitation problems
120 119 *in_filter_generator(Repository.repo_id, allowed_ids)
121 120 ))
122 121
122 query = query.order_by(case(
123 [
124 (Repository.repo_name.startswith(repo_group_name), repo_group_name+'/'),
125 ],
126 ))
127 query = query.order_by(func.length(Repository.repo_name))
128 query = query.order_by(Repository.repo_name)
129
123 130 if repo_type:
124 131 query = query.filter(Repository.repo_type == repo_type)
125 132
@@ -145,20 +152,26 b' class HomeView(BaseAppView):'
145 152 }
146 153 for obj in acl_iter]
147 154
148 def _get_repo_group_list(self, name_contains=None, limit=20):
155 def _get_repo_group_list(self, name_contains=None, repo_group_name='', limit=20):
149 156 org_query = name_contains
150 157 allowed_ids = self._rhodecode_user.repo_group_acl_ids(
151 158 ['group.read', 'group.write', 'group.admin'],
152 159 cache=False, name_filter=name_contains) or [-1]
153 160
154 161 query = RepoGroup.query()\
155 .order_by(func.length(RepoGroup.group_name))\
156 .order_by(RepoGroup.group_name) \
157 162 .filter(or_(
158 163 # generate multiple IN to fix limitation problems
159 164 *in_filter_generator(RepoGroup.group_id, allowed_ids)
160 165 ))
161 166
167 query = query.order_by(case(
168 [
169 (RepoGroup.group_name.startswith(repo_group_name), repo_group_name+'/'),
170 ],
171 ))
172 query = query.order_by(func.length(RepoGroup.group_name))
173 query = query.order_by(RepoGroup.group_name)
174
162 175 if name_contains:
163 176 ilike_expression = u'%{}%'.format(safe_unicode(name_contains))
164 177 query = query.filter(
@@ -183,11 +196,17 b' class HomeView(BaseAppView):'
183 196 def _get_user_list(self, name_contains=None, limit=20):
184 197 org_query = name_contains
185 198 if not name_contains:
186 return []
199 return [], False
187 200
188 name_contains = re.compile('(?:user:)(.+)').findall(name_contains)
201 # TODO(marcink): should all logged in users be allowed to search others?
202 allowed_user_search = self._rhodecode_user.username != User.DEFAULT_USER
203 if not allowed_user_search:
204 return [], False
205
206 name_contains = re.compile('(?:user:[ ]?)(.+)').findall(name_contains)
189 207 if len(name_contains) != 1:
190 return []
208 return [], False
209
191 210 name_contains = name_contains[0]
192 211
193 212 query = User.query()\
@@ -207,22 +226,28 b' class HomeView(BaseAppView):'
207 226 {
208 227 'id': obj.user_id,
209 228 'value': org_query,
210 'value_display': obj.username,
229 'value_display': 'user: `{}`'.format(obj.username),
211 230 'type': 'user',
212 231 'icon_link': h.gravatar_url(obj.email, 30),
213 232 'url': h.route_path(
214 233 'user_profile', username=obj.username)
215 234 }
216 for obj in acl_iter]
235 for obj in acl_iter], True
217 236
218 237 def _get_user_groups_list(self, name_contains=None, limit=20):
219 238 org_query = name_contains
220 239 if not name_contains:
221 return []
240 return [], False
222 241
223 name_contains = re.compile('(?:user_group:)(.+)').findall(name_contains)
242 # TODO(marcink): should all logged in users be allowed to search others?
243 allowed_user_search = self._rhodecode_user.username != User.DEFAULT_USER
244 if not allowed_user_search:
245 return [], False
246
247 name_contains = re.compile('(?:user_group:[ ]?)(.+)').findall(name_contains)
224 248 if len(name_contains) != 1:
225 return []
249 return [], False
250
226 251 name_contains = name_contains[0]
227 252
228 253 query = UserGroup.query()\
@@ -241,27 +266,34 b' class HomeView(BaseAppView):'
241 266 {
242 267 'id': obj.users_group_id,
243 268 'value': org_query,
244 'value_display': obj.users_group_name,
269 'value_display': 'user_group: `{}`'.format(obj.users_group_name),
245 270 'type': 'user_group',
246 271 'url': h.route_path(
247 272 'user_group_profile', user_group_name=obj.users_group_name)
248 273 }
249 for obj in acl_iter]
274 for obj in acl_iter], True
250 275
251 def _get_hash_commit_list(self, auth_user, searcher, query):
276 def _get_hash_commit_list(self, auth_user, searcher, query, repo=None, repo_group=None):
277 repo_name = repo_group_name = None
278 if repo:
279 repo_name = repo.repo_name
280 if repo_group:
281 repo_group_name = repo_group.group_name
282
252 283 org_query = query
253 284 if not query or len(query) < 3 or not searcher:
254 return []
285 return [], False
255 286
256 commit_hashes = re.compile('(?:commit:)([0-9a-f]{2,40})').findall(query)
287 commit_hashes = re.compile('(?:commit:[ ]?)([0-9a-f]{2,40})').findall(query)
257 288
258 289 if len(commit_hashes) != 1:
259 return []
290 return [], False
291
260 292 commit_hash = commit_hashes[0]
261 293
262 294 result = searcher.search(
263 295 'commit_id:{}*'.format(commit_hash), 'commit', auth_user,
264 raise_on_exc=False)
296 repo_name, repo_group_name, raise_on_exc=False)
265 297
266 298 commits = []
267 299 for entry in result['results']:
@@ -286,7 +318,55 b' class HomeView(BaseAppView):'
286 318 }
287 319
288 320 commits.append(commit_entry)
289 return commits
321 return commits, True
322
323 def _get_path_list(self, auth_user, searcher, query, repo=None, repo_group=None):
324 repo_name = repo_group_name = None
325 if repo:
326 repo_name = repo.repo_name
327 if repo_group:
328 repo_group_name = repo_group.group_name
329
330 org_query = query
331 if not query or len(query) < 3 or not searcher:
332 return [], False
333
334 paths_re = re.compile('(?:file:[ ]?)(.+)').findall(query)
335 if len(paths_re) != 1:
336 return [], False
337
338 file_path = paths_re[0]
339
340 search_path = searcher.escape_specials(file_path)
341 result = searcher.search(
342 'file.raw:*{}*'.format(search_path), 'path', auth_user,
343 repo_name, repo_group_name, raise_on_exc=False)
344
345 files = []
346 for entry in result['results']:
347 repo_data = {
348 'repository_id': entry.get('repository_id'),
349 'repository_type': entry.get('repo_type'),
350 'repository_name': entry.get('repository'),
351 }
352
353 file_entry = {
354 'id': entry['commit_id'],
355 'value': org_query,
356 'value_display': '`{}` file: {}'.format(
357 entry['repository'], entry['file']),
358 'type': 'file',
359 'repo': entry['repository'],
360 'repo_data': repo_data,
361
362 'url': h.route_path(
363 'repo_files',
364 repo_name=entry['repository'], commit_id=entry['commit_id'],
365 f_path=entry['file'])
366 }
367
368 files.append(file_entry)
369 return files, True
290 370
291 371 @LoginRequired()
292 372 @view_config(
@@ -363,36 +443,42 b' class HomeView(BaseAppView):'
363 443 def query_modifier():
364 444 qry = query
365 445 return {'q': qry, 'type': 'content'}
366 label = u'File search for `{}` in this repository.'.format(query)
367 queries.append(
368 {
369 'id': -10,
370 'value': query,
371 'value_display': label,
372 'type': 'search',
373 'url': h.route_path('search_repo',
374 repo_name=repo_name,
375 _query=query_modifier())
446
447 label = u'File search for `{}`'.format(h.escape(query))
448 file_qry = {
449 'id': -10,
450 'value': query,
451 'value_display': label,
452 'type': 'search',
453 'subtype': 'repo',
454 'url': h.route_path('search_repo',
455 repo_name=repo_name,
456 _query=query_modifier())
376 457 }
377 )
378 458
379 459 # commits
380 460 def query_modifier():
381 461 qry = query
382 462 return {'q': qry, 'type': 'commit'}
383 463
384 label = u'Commit search for `{}` in this repository.'.format(query)
385 queries.append(
386 {
387 'id': -20,
388 'value': query,
389 'value_display': label,
390 'type': 'search',
391 'url': h.route_path('search_repo',
392 repo_name=repo_name,
393 _query=query_modifier())
464 label = u'Commit search for `{}`'.format(h.escape(query))
465 commit_qry = {
466 'id': -20,
467 'value': query,
468 'value_display': label,
469 'type': 'search',
470 'subtype': 'repo',
471 'url': h.route_path('search_repo',
472 repo_name=repo_name,
473 _query=query_modifier())
394 474 }
395 )
475
476 if repo_context in ['commit', 'commits']:
477 queries.extend([commit_qry, file_qry])
478 elif repo_context in ['files', 'summary']:
479 queries.extend([file_qry, commit_qry])
480 else:
481 queries.extend([commit_qry, file_qry])
396 482
397 483 elif is_es_6 and repo_group_name:
398 484 # files
@@ -400,37 +486,43 b' class HomeView(BaseAppView):'
400 486 qry = query
401 487 return {'q': qry, 'type': 'content'}
402 488
403 label = u'File search for `{}` in this repository group'.format(query)
404 queries.append(
405 {
406 'id': -30,
407 'value': query,
408 'value_display': label,
409 'type': 'search',
410 'url': h.route_path('search_repo_group',
411 repo_group_name=repo_group_name,
412 _query=query_modifier())
489 label = u'File search for `{}`'.format(query)
490 file_qry = {
491 'id': -30,
492 'value': query,
493 'value_display': label,
494 'type': 'search',
495 'subtype': 'repo_group',
496 'url': h.route_path('search_repo_group',
497 repo_group_name=repo_group_name,
498 _query=query_modifier())
413 499 }
414 )
415 500
416 501 # commits
417 502 def query_modifier():
418 503 qry = query
419 504 return {'q': qry, 'type': 'commit'}
420 505
421 label = u'Commit search for `{}` in this repository group'.format(query)
422 queries.append(
423 {
424 'id': -40,
425 'value': query,
426 'value_display': label,
427 'type': 'search',
428 'url': h.route_path('search_repo_group',
429 repo_group_name=repo_group_name,
430 _query=query_modifier())
506 label = u'Commit search for `{}`'.format(query)
507 commit_qry = {
508 'id': -40,
509 'value': query,
510 'value_display': label,
511 'type': 'search',
512 'subtype': 'repo_group',
513 'url': h.route_path('search_repo_group',
514 repo_group_name=repo_group_name,
515 _query=query_modifier())
431 516 }
432 )
433 517
518 if repo_context in ['commit', 'commits']:
519 queries.extend([commit_qry, file_qry])
520 elif repo_context in ['files', 'summary']:
521 queries.extend([file_qry, commit_qry])
522 else:
523 queries.extend([commit_qry, file_qry])
524
525 # Global, not scoped
434 526 if not queries:
435 527 queries.append(
436 528 {
@@ -438,6 +530,7 b' class HomeView(BaseAppView):'
438 530 'value': query,
439 531 'value_display': u'File search for: `{}`'.format(query),
440 532 'type': 'search',
533 'subtype': 'global',
441 534 'url': h.route_path('search',
442 535 _query={'q': query, 'type': 'content'})
443 536 })
@@ -447,6 +540,7 b' class HomeView(BaseAppView):'
447 540 'value': query,
448 541 'value_display': u'Commit search for: `{}`'.format(query),
449 542 'type': 'search',
543 'subtype': 'global',
450 544 'url': h.route_path('search',
451 545 _query={'q': query, 'type': 'commit'})
452 546 })
@@ -469,54 +563,107 b' class HomeView(BaseAppView):'
469 563 if not query:
470 564 return {'suggestions': res}
471 565
566 def no_match(name):
567 return {
568 'id': -1,
569 'value': "",
570 'value_display': name,
571 'type': 'text',
572 'url': ""
573 }
472 574 searcher = searcher_from_config(self.request.registry.settings)
473 for _q in self._get_default_search_queries(self.request.GET, searcher, query):
474 res.append(_q)
575 has_specialized_search = False
475 576
577 # set repo context
578 repo = None
579 repo_id = safe_int(self.request.GET.get('search_context[repo_id]'))
580 if repo_id:
581 repo = Repository.get(repo_id)
582
583 # set group context
584 repo_group = None
476 585 repo_group_id = safe_int(self.request.GET.get('search_context[repo_group_id]'))
477 586 if repo_group_id:
478 587 repo_group = RepoGroup.get(repo_group_id)
479 composed_hint = '{}/{}'.format(repo_group.group_name, query)
480 show_hint = not query.startswith(repo_group.group_name)
481 if repo_group and show_hint:
482 hint = u'Repository search inside: `{}`'.format(composed_hint)
483 res.append({
484 'id': -1,
485 'value': composed_hint,
486 'value_display': hint,
487 'type': 'hint',
488 'url': ""
489 })
588 prefix_match = False
589
590 # user: type search
591 if not prefix_match:
592 users, prefix_match = self._get_user_list(query)
593 if users:
594 has_specialized_search = True
595 for serialized_user in users:
596 res.append(serialized_user)
597 elif prefix_match:
598 has_specialized_search = True
599 res.append(no_match('No matching users found'))
490 600
491 repo_groups = self._get_repo_group_list(query)
492 for serialized_repo_group in repo_groups:
493 res.append(serialized_repo_group)
601 # user_group: type search
602 if not prefix_match:
603 user_groups, prefix_match = self._get_user_groups_list(query)
604 if user_groups:
605 has_specialized_search = True
606 for serialized_user_group in user_groups:
607 res.append(serialized_user_group)
608 elif prefix_match:
609 has_specialized_search = True
610 res.append(no_match('No matching user groups found'))
494 611
495 repos = self._get_repo_list(query)
496 for serialized_repo in repos:
497 res.append(serialized_repo)
612 # FTS commit: type search
613 if not prefix_match:
614 commits, prefix_match = self._get_hash_commit_list(
615 c.auth_user, searcher, query, repo, repo_group)
616 if commits:
617 has_specialized_search = True
618 unique_repos = collections.OrderedDict()
619 for commit in commits:
620 repo_name = commit['repo']
621 unique_repos.setdefault(repo_name, []).append(commit)
498 622
499 # TODO(marcink): should all logged in users be allowed to search others?
500 allowed_user_search = self._rhodecode_user.username != User.DEFAULT_USER
501 if allowed_user_search:
502 users = self._get_user_list(query)
503 for serialized_user in users:
504 res.append(serialized_user)
623 for _repo, commits in unique_repos.items():
624 for commit in commits:
625 res.append(commit)
626 elif prefix_match:
627 has_specialized_search = True
628 res.append(no_match('No matching commits found'))
505 629
506 user_groups = self._get_user_groups_list(query)
507 for serialized_user_group in user_groups:
508 res.append(serialized_user_group)
630 # FTS file: type search
631 if not prefix_match:
632 paths, prefix_match = self._get_path_list(
633 c.auth_user, searcher, query, repo, repo_group)
634 if paths:
635 has_specialized_search = True
636 unique_repos = collections.OrderedDict()
637 for path in paths:
638 repo_name = path['repo']
639 unique_repos.setdefault(repo_name, []).append(path)
509 640
510 commits = self._get_hash_commit_list(c.auth_user, searcher, query)
511 if commits:
512 unique_repos = collections.OrderedDict()
513 for commit in commits:
514 repo_name = commit['repo']
515 unique_repos.setdefault(repo_name, []).append(commit)
641 for repo, paths in unique_repos.items():
642 for path in paths:
643 res.append(path)
644 elif prefix_match:
645 has_specialized_search = True
646 res.append(no_match('No matching files found'))
647
648 # main suggestions
649 if not has_specialized_search:
650 repo_group_name = ''
651 if repo_group:
652 repo_group_name = repo_group.group_name
516 653
517 for repo, commits in unique_repos.items():
518 for commit in commits:
519 res.append(commit)
654 for _q in self._get_default_search_queries(self.request.GET, searcher, query):
655 res.append(_q)
656
657 repo_groups = self._get_repo_group_list(query, repo_group_name=repo_group_name)
658 for serialized_repo_group in repo_groups:
659 res.append(serialized_repo_group)
660
661 repos = self._get_repo_list(query, repo_group_name=repo_group_name)
662 for serialized_repo in repos:
663 res.append(serialized_repo)
664
665 if not repos and not repo_groups:
666 res.append(no_match('No matches found'))
520 667
521 668 return {'suggestions': res}
522 669
@@ -564,8 +711,11 b' class HomeView(BaseAppView):'
564 711 def repo_group_main_page(self):
565 712 c = self.load_default_context()
566 713 c.repo_group = self.request.db_repo_group
567 repo_data, repo_group_data = self._get_groups_and_repos(
568 c.repo_group.group_id)
714 repo_data, repo_group_data = self._get_groups_and_repos(c.repo_group.group_id)
715
716 # update every 5 min
717 if self.request.db_repo_group.last_commit_cache_update_diff > 60 * 5:
718 self.request.db_repo_group.update_commit_cache()
569 719
570 720 # json used to render the grids
571 721 c.repos_data = json.dumps(repo_data)
@@ -594,6 +744,34 b' class HomeView(BaseAppView):'
594 744 @LoginRequired()
595 745 @CSRFRequired()
596 746 @view_config(
747 route_name='file_preview', request_method='POST',
748 renderer='string', xhr=True)
749 def file_preview(self):
750 # Technically a CSRF token is not needed as no state changes with this
751 # call. However, as this is a POST is better to have it, so automated
752 # tools don't flag it as potential CSRF.
753 # Post is required because the payload could be bigger than the maximum
754 # allowed by GET.
755
756 text = self.request.POST.get('text')
757 file_path = self.request.POST.get('file_path')
758
759 renderer = h.renderer_from_filename(file_path)
760
761 if renderer:
762 return h.render(text, renderer=renderer, mentions=True)
763 else:
764 self.load_default_context()
765 _render = self.request.get_partial_renderer(
766 'rhodecode:templates/files/file_content.mako')
767
768 lines = filenode_as_lines_tokens(FileNode(file_path, text))
769
770 return _render('render_lines', lines)
771
772 @LoginRequired()
773 @CSRFRequired()
774 @view_config(
597 775 route_name='store_user_session_value', request_method='POST',
598 776 renderer='string', xhr=True)
599 777 def store_user_session_attr(self):
@@ -604,4 +782,4 b' class HomeView(BaseAppView):'
604 782 if existing_value != val:
605 783 self.request.session[key] = val
606 784
607 return 'stored:{}'.format(key)
785 return 'stored:{}:{}'.format(key, val)
@@ -31,12 +31,12 b' from pyramid.renderers import render'
31 31
32 32 from rhodecode.apps._base import BaseAppView
33 33 from rhodecode.model.db import (
34 or_, joinedload, UserLog, UserFollowing, User, UserApiKeys)
34 or_, joinedload, Repository, UserLog, UserFollowing, User, UserApiKeys)
35 35 from rhodecode.model.meta import Session
36 36 import rhodecode.lib.helpers as h
37 37 from rhodecode.lib.helpers import Page
38 38 from rhodecode.lib.user_log_filter import user_log_filter
39 from rhodecode.lib.auth import LoginRequired, NotAnonymous, CSRFRequired
39 from rhodecode.lib.auth import LoginRequired, NotAnonymous, CSRFRequired, HasRepoPermissionAny
40 40 from rhodecode.lib.utils2 import safe_int, AttributeDict, md5_safe
41 41 from rhodecode.model.scm import ScmModel
42 42
@@ -153,7 +153,7 b' class JournalView(BaseAppView):'
153 153 desc = action_extra()
154 154 _url = h.route_url('home')
155 155 if entry.repository is not None:
156 _url = h.route_url('repo_changelog',
156 _url = h.route_url('repo_commits',
157 157 repo_name=entry.repository.repo_name)
158 158
159 159 feed.add_item(
@@ -199,7 +199,7 b' class JournalView(BaseAppView):'
199 199 desc = action_extra()
200 200 _url = h.route_url('home')
201 201 if entry.repository is not None:
202 _url = h.route_url('repo_changelog',
202 _url = h.route_url('repo_commits',
203 203 repo_name=entry.repository.repo_name)
204 204
205 205 feed.add_item(
@@ -297,18 +297,19 b' class JournalView(BaseAppView):'
297 297 user_id = self.request.POST.get('follows_user_id')
298 298 if user_id:
299 299 try:
300 ScmModel().toggle_following_user(
301 user_id, self._rhodecode_user.user_id)
300 ScmModel().toggle_following_user(user_id, self._rhodecode_user.user_id)
302 301 Session().commit()
303 302 return 'ok'
304 303 except Exception:
305 304 raise HTTPBadRequest()
306 305
307 306 repo_id = self.request.POST.get('follows_repo_id')
308 if repo_id:
307 repo = Repository.get_or_404(repo_id)
308 perm_set = ['repository.read', 'repository.write', 'repository.admin']
309 has_perm = HasRepoPermissionAny(*perm_set)(repo.repo_name, 'RepoWatch check')
310 if repo and has_perm:
309 311 try:
310 ScmModel().toggle_following_repo(
311 repo_id, self._rhodecode_user.user_id)
312 ScmModel().toggle_following_repo(repo_id, self._rhodecode_user.user_id)
312 313 Session().commit()
313 314 return 'ok'
314 315 except Exception:
@@ -160,4 +160,4 b' class TestMyAccountSshKeysView(TestContr'
160 160
161 161 response.mustcontain('Private key')
162 162 response.mustcontain('Public key')
163 response.mustcontain('-----BEGIN RSA PRIVATE KEY-----')
163 response.mustcontain('-----BEGIN PRIVATE KEY-----')
@@ -360,7 +360,7 b' class MyAccountView(BaseAppView, DataGri'
360 360 'repository.read', 'repository.write', 'repository.admin'])
361 361
362 362 repos_data = RepoModel().get_repos_as_dict(
363 repo_list=repo_list, admin=admin)
363 repo_list=repo_list, admin=admin, short_name=False)
364 364 # json used to render the grid
365 365 return json.dumps(repos_data)
366 366
@@ -423,7 +423,7 b' class MyAccountView(BaseAppView, DataGri'
423 423 default_redirect_url = ''
424 424
425 425 # save repo
426 if entry.get('bookmark_repo'):
426 if entry.get('bookmark_repo') and safe_int(entry.get('bookmark_repo')):
427 427 repo = Repository.get(entry['bookmark_repo'])
428 428 perm_check = HasRepoPermissionAny(
429 429 'repository.read', 'repository.write', 'repository.admin')
@@ -432,7 +432,7 b' class MyAccountView(BaseAppView, DataGri'
432 432 should_save = True
433 433 default_redirect_url = '${repo_url}'
434 434 # save repo group
435 elif entry.get('bookmark_repo_group'):
435 elif entry.get('bookmark_repo_group') and safe_int(entry.get('bookmark_repo_group')):
436 436 repo_group = RepoGroup.get(entry['bookmark_repo_group'])
437 437 perm_check = HasRepoGroupPermissionAny(
438 438 'group.read', 'group.write', 'group.admin')
@@ -496,6 +496,7 b' class MyAccountView(BaseAppView, DataGri'
496 496 if not user_bookmark:
497 497 raise HTTPFound(redirect_url)
498 498
499 # repository set
499 500 if user_bookmark.repository:
500 501 repo_name = user_bookmark.repository.repo_name
501 502 base_redirect_url = h.route_path(
@@ -506,7 +507,7 b' class MyAccountView(BaseAppView, DataGri'
506 507 .safe_substitute({'repo_url': base_redirect_url})
507 508 else:
508 509 redirect_url = base_redirect_url
509
510 # repository group set
510 511 elif user_bookmark.repository_group:
511 512 repo_group_name = user_bookmark.repository_group.group_name
512 513 base_redirect_url = h.route_path(
@@ -517,9 +518,11 b' class MyAccountView(BaseAppView, DataGri'
517 518 .safe_substitute({'repo_group_url': base_redirect_url})
518 519 else:
519 520 redirect_url = base_redirect_url
520
521 # custom URL set
521 522 elif user_bookmark.redirect_url:
522 redirect_url = user_bookmark.redirect_url
523 server_url = h.route_url('home').rstrip('/')
524 redirect_url = string.Template(user_bookmark.redirect_url) \
525 .safe_substitute({'server_url': server_url})
523 526
524 527 log.debug('Redirecting bookmark %s to %s', user_bookmark, redirect_url)
525 528 raise HTTPFound(redirect_url)
@@ -90,7 +90,7 b' def includeme(config):'
90 90 # Files
91 91 config.add_route(
92 92 name='repo_archivefile',
93 pattern='/{repo_name:.*?[^/]}/archive/{fname}', repo_route=True)
93 pattern='/{repo_name:.*?[^/]}/archive/{fname:.*}', repo_route=True)
94 94
95 95 config.add_route(
96 96 name='repo_files_diff',
@@ -172,6 +172,10 b' def includeme(config):'
172 172 pattern='/{repo_name:.*?[^/]}/add_file/{commit_id}/{f_path:.*}',
173 173 repo_route=True)
174 174 config.add_route(
175 name='repo_files_upload_file',
176 pattern='/{repo_name:.*?[^/]}/upload_file/{commit_id}/{f_path:.*}',
177 repo_route=True)
178 config.add_route(
175 179 name='repo_files_create_file',
176 180 pattern='/{repo_name:.*?[^/]}/create_file/{commit_id}/{f_path:.*}',
177 181 repo_route=True)
@@ -189,19 +193,27 b' def includeme(config):'
189 193 name='repo_stats',
190 194 pattern='/{repo_name:.*?[^/]}/repo_stats/{commit_id}', repo_route=True)
191 195
192 # Changelog
196 # Commits
197 config.add_route(
198 name='repo_commits',
199 pattern='/{repo_name:.*?[^/]}/commits', repo_route=True)
200 config.add_route(
201 name='repo_commits_file',
202 pattern='/{repo_name:.*?[^/]}/commits/{commit_id}/{f_path:.*}', repo_route=True)
203 config.add_route(
204 name='repo_commits_elements',
205 pattern='/{repo_name:.*?[^/]}/commits_elements', repo_route=True)
206 config.add_route(
207 name='repo_commits_elements_file',
208 pattern='/{repo_name:.*?[^/]}/commits_elements/{commit_id}/{f_path:.*}', repo_route=True)
209
210 # Changelog (old deprecated name for commits page)
193 211 config.add_route(
194 212 name='repo_changelog',
195 213 pattern='/{repo_name:.*?[^/]}/changelog', repo_route=True)
196 214 config.add_route(
197 215 name='repo_changelog_file',
198 216 pattern='/{repo_name:.*?[^/]}/changelog/{commit_id}/{f_path:.*}', repo_route=True)
199 config.add_route(
200 name='repo_changelog_elements',
201 pattern='/{repo_name:.*?[^/]}/changelog_elements', repo_route=True)
202 config.add_route(
203 name='repo_changelog_elements_file',
204 pattern='/{repo_name:.*?[^/]}/changelog_elements/{commit_id}/{f_path:.*}', repo_route=True)
205 217
206 218 # Compare
207 219 config.add_route(
@@ -312,6 +324,11 b' def includeme(config):'
312 324 pattern='/{repo_name:.*?[^/]}/pull-request/{pull_request_id:\d+}/comment/{comment_id}/delete',
313 325 repo_route=True, repo_accepted_types=['hg', 'git'])
314 326
327 # Artifacts, (EE feature)
328 config.add_route(
329 name='repo_artifacts_list',
330 pattern='/{repo_name:.*?[^/]}/artifacts', repo_route=True)
331
315 332 # Settings
316 333 config.add_route(
317 334 name='edit_repo',
@@ -40,11 +40,11 b' def route_path(name, params=None, **kwar'
40 40 class TestPullRequestList(object):
41 41
42 42 @pytest.mark.parametrize('params, expected_title', [
43 ({'source': 0, 'closed': 1}, 'Closed Pull Requests'),
44 ({'source': 0, 'my': 1}, 'opened by me'),
45 ({'source': 0, 'awaiting_review': 1}, 'awaiting review'),
46 ({'source': 0, 'awaiting_my_review': 1}, 'awaiting my review'),
47 ({'source': 1}, 'Pull Requests from'),
43 ({'source': 0, 'closed': 1}, 'Closed'),
44 ({'source': 0, 'my': 1}, 'Opened by me'),
45 ({'source': 0, 'awaiting_review': 1}, 'Awaiting review'),
46 ({'source': 0, 'awaiting_my_review': 1}, 'Awaiting my review'),
47 ({'source': 1}, 'From this repo'),
48 48 ])
49 49 def test_showing_list_page(self, backend, pr_util, params, expected_title):
50 50 pull_request = pr_util.create_pull_request()
@@ -55,9 +55,10 b' class TestPullRequestList(object):'
55 55 params=params))
56 56
57 57 assert_response = response.assert_response()
58 assert_response.element_equals_to('.panel-title', expected_title)
59 element = assert_response.get_element('.panel-title')
60 element_text = assert_response._element_to_string(element)
58
59 element = assert_response.get_element('.title .active')
60 element_text = element.text_content()
61 assert expected_title == element_text
61 62
62 63 def test_showing_list_page_data(self, backend, pr_util, xhr_header):
63 64 pull_request = pr_util.create_pull_request()
@@ -32,9 +32,10 b' def route_path(name, params=None, **kwar'
32 32 import urllib
33 33
34 34 base_url = {
35 'repo_changelog':'/{repo_name}/changelog',
36 'repo_changelog_file':'/{repo_name}/changelog/{commit_id}/{f_path}',
37 'repo_changelog_elements':'/{repo_name}/changelog_elements',
35 'repo_changelog': '/{repo_name}/changelog',
36 'repo_commits': '/{repo_name}/commits',
37 'repo_commits_file': '/{repo_name}/commits/{commit_id}/{f_path}',
38 'repo_commits_elements': '/{repo_name}/commits_elements',
38 39 }[name].format(**kwargs)
39 40
40 41 if params:
@@ -42,8 +43,22 b' def route_path(name, params=None, **kwar'
42 43 return base_url
43 44
44 45
46 def assert_commits_on_page(response, indexes):
47 found_indexes = [int(idx) for idx in MATCH_HASH.findall(response.body)]
48 assert found_indexes == indexes
49
50
45 51 class TestChangelogController(TestController):
46 52
53 def test_commits_page(self, backend):
54 self.log_user()
55 response = self.app.get(
56 route_path('repo_commits', repo_name=backend.repo_name))
57
58 first_idx = -1
59 last_idx = -DEFAULT_CHANGELOG_SIZE
60 self.assert_commit_range_on_page(response, first_idx, last_idx, backend)
61
47 62 def test_changelog(self, backend):
48 63 self.log_user()
49 64 response = self.app.get(
@@ -62,6 +77,14 b' class TestChangelogController(TestContro'
62 77 params=dict(branch=backend.default_branch_name)),
63 78 status=200)
64 79
80 @pytest.mark.backends("hg", "git")
81 def test_commits_filtered_by_branch(self, backend):
82 self.log_user()
83 self.app.get(
84 route_path('repo_commits', repo_name=backend.repo_name,
85 params=dict(branch=backend.default_branch_name)),
86 status=200)
87
65 88 @pytest.mark.backends("svn")
66 89 def test_changelog_filtered_by_branch_svn(self, autologin_user, backend):
67 90 repo = backend['svn-simple-layout']
@@ -70,27 +93,22 b' class TestChangelogController(TestContro'
70 93 params=dict(branch='trunk')),
71 94 status=200)
72 95
73 self.assert_commits_on_page(
74 response, indexes=[15, 12, 7, 3, 2, 1])
96 assert_commits_on_page(response, indexes=[15, 12, 7, 3, 2, 1])
75 97
76 def test_changelog_filtered_by_wrong_branch(self, backend):
98 def test_commits_filtered_by_wrong_branch(self, backend):
77 99 self.log_user()
78 100 branch = 'wrong-branch-name'
79 101 response = self.app.get(
80 route_path('repo_changelog', repo_name=backend.repo_name,
102 route_path('repo_commits', repo_name=backend.repo_name,
81 103 params=dict(branch=branch)),
82 104 status=302)
83 expected_url = '/{repo}/changelog/{branch}'.format(
105 expected_url = '/{repo}/commits/{branch}'.format(
84 106 repo=backend.repo_name, branch=branch)
85 107 assert expected_url in response.location
86 108 response = response.follow()
87 109 expected_warning = 'Branch {} is not found.'.format(branch)
88 110 assert expected_warning in response.body
89 111
90 def assert_commits_on_page(self, response, indexes):
91 found_indexes = [int(idx) for idx in MATCH_HASH.findall(response.body)]
92 assert found_indexes == indexes
93
94 112 @pytest.mark.xfail_backends("svn", reason="Depends on branch support")
95 113 def test_changelog_filtered_by_branch_with_merges(
96 114 self, autologin_user, backend):
@@ -112,21 +130,20 b' class TestChangelogController(TestContro'
112 130 status=200)
113 131
114 132 @pytest.mark.backends("hg")
115 def test_changelog_closed_branches(self, autologin_user, backend):
133 def test_commits_closed_branches(self, autologin_user, backend):
116 134 repo = backend['closed_branch']
117 135 response = self.app.get(
118 route_path('repo_changelog', repo_name=repo.repo_name,
136 route_path('repo_commits', repo_name=repo.repo_name,
119 137 params=dict(branch='experimental')),
120 138 status=200)
121 139
122 self.assert_commits_on_page(
123 response, indexes=[3, 1])
140 assert_commits_on_page(response, indexes=[3, 1])
124 141
125 142 def test_changelog_pagination(self, backend):
126 143 self.log_user()
127 144 # pagination, walk up to page 6
128 145 changelog_url = route_path(
129 'repo_changelog', repo_name=backend.repo_name)
146 'repo_commits', repo_name=backend.repo_name)
130 147
131 148 for page in range(1, 7):
132 149 response = self.app.get(changelog_url, {'page': page})
@@ -138,22 +155,30 b' class TestChangelogController(TestContro'
138 155 def assert_commit_range_on_page(
139 156 self, response, first_idx, last_idx, backend):
140 157 input_template = (
141 """<input class="commit-range" id="%(raw_id)s" """
158 """<input class="commit-range" """
159 """data-commit-id="%(raw_id)s" data-commit-idx="%(idx)s" """
160 """data-short-id="%(short_id)s" id="%(raw_id)s" """
142 161 """name="%(raw_id)s" type="checkbox" value="1" />"""
143 162 )
163
144 164 commit_span_template = """<span class="commit_hash">r%s:%s</span>"""
145 165 repo = backend.repo
146 166
147 167 first_commit_on_page = repo.get_commit(commit_idx=first_idx)
148 168 response.mustcontain(
149 input_template % {'raw_id': first_commit_on_page.raw_id})
169 input_template % {'raw_id': first_commit_on_page.raw_id,
170 'idx': first_commit_on_page.idx,
171 'short_id': first_commit_on_page.short_id})
172
150 173 response.mustcontain(commit_span_template % (
151 174 first_commit_on_page.idx, first_commit_on_page.short_id)
152 175 )
153 176
154 177 last_commit_on_page = repo.get_commit(commit_idx=last_idx)
155 178 response.mustcontain(
156 input_template % {'raw_id': last_commit_on_page.raw_id})
179 input_template % {'raw_id': last_commit_on_page.raw_id,
180 'idx': last_commit_on_page.idx,
181 'short_id': last_commit_on_page.short_id})
157 182 response.mustcontain(commit_span_template % (
158 183 last_commit_on_page.idx, last_commit_on_page.short_id)
159 184 )
@@ -168,10 +193,10 b' class TestChangelogController(TestContro'
168 193 '/vcs/exceptions.py',
169 194 '//vcs/exceptions.py'
170 195 ])
171 def test_changelog_with_filenode(self, backend, test_path):
196 def test_commits_with_filenode(self, backend, test_path):
172 197 self.log_user()
173 198 response = self.app.get(
174 route_path('repo_changelog_file', repo_name=backend.repo_name,
199 route_path('repo_commits_file', repo_name=backend.repo_name,
175 200 commit_id='tip', f_path=test_path),
176 201 )
177 202
@@ -180,16 +205,16 b' class TestChangelogController(TestContro'
180 205 response.mustcontain('Added not implemented hg backend test case')
181 206 response.mustcontain('Added BaseChangeset class')
182 207
183 def test_changelog_with_filenode_that_is_dirnode(self, backend):
208 def test_commits_with_filenode_that_is_dirnode(self, backend):
184 209 self.log_user()
185 210 self.app.get(
186 route_path('repo_changelog_file', repo_name=backend.repo_name,
211 route_path('repo_commits_file', repo_name=backend.repo_name,
187 212 commit_id='tip', f_path='/tests'),
188 213 status=302)
189 214
190 def test_changelog_with_filenode_not_existing(self, backend):
215 def test_commits_with_filenode_not_existing(self, backend):
191 216 self.log_user()
192 217 self.app.get(
193 route_path('repo_changelog_file', repo_name=backend.repo_name,
218 route_path('repo_commits_file', repo_name=backend.repo_name,
194 219 commit_id='tip', f_path='wrong_path'),
195 220 status=302)
@@ -94,6 +94,7 b' class TestCompareView(object):'
94 94 origin_repo = origin.scm_instance(cache=False)
95 95 origin_repo.config.clear_section('hooks')
96 96 origin_repo.pull(fork.repo_full_path, commit_ids=[commit3.raw_id])
97 origin_repo = origin.scm_instance(cache=False) # cache rebuild
97 98
98 99 # Verify test fixture setup
99 100 # This does not work for git
@@ -162,8 +163,7 b' class TestCompareView(object):'
162 163 compare_page.target_source_are_disabled()
163 164
164 165 @pytest.mark.xfail_backends("svn", reason="Depends on branch support")
165 def test_compare_forks_on_branch_extra_commits_origin_has_incomming(
166 self, backend):
166 def test_compare_forks_on_branch_extra_commits_origin_has_incomming(self, backend):
167 167 repo1 = backend.create_repo()
168 168
169 169 # commit something !
@@ -21,6 +21,7 b''
21 21 import pytest
22 22
23 23 from rhodecode.lib.vcs import nodes
24 from rhodecode.lib.vcs.backends.base import EmptyCommit
24 25 from rhodecode.tests.fixture import Fixture
25 26 from rhodecode.tests.utils import commit_change
26 27
@@ -43,70 +44,7 b' def route_path(name, params=None, **kwar'
43 44 @pytest.mark.usefixtures("autologin_user", "app")
44 45 class TestSideBySideDiff(object):
45 46
46 def test_diff_side_by_side(self, app, backend, backend_stub):
47 f_path = 'test_sidebyside_file.py'
48 commit1_content = 'content-25d7e49c18b159446c\n'
49 commit2_content = 'content-603d6c72c46d953420\n'
50 repo = backend.create_repo()
51
52 commit1 = commit_change(
53 repo.repo_name, filename=f_path, content=commit1_content,
54 message='A', vcs_type=backend.alias, parent=None, newfile=True)
55
56 commit2 = commit_change(
57 repo.repo_name, filename=f_path, content=commit2_content,
58 message='B, child of A', vcs_type=backend.alias, parent=commit1)
59
60 response = self.app.get(route_path(
61 'repo_compare',
62 repo_name=repo.repo_name,
63 source_ref_type='rev',
64 source_ref=commit1.raw_id,
65 target_ref_type='rev',
66 target_ref=commit2.raw_id,
67 params=dict(f_path=f_path, target_repo=repo.repo_name, diffmode='sidebyside')
68 ))
69
70 response.mustcontain('Expand 1 commit')
71 response.mustcontain('1 file changed')
72
73 response.mustcontain(
74 'r%s:%s...r%s:%s' % (
75 commit1.idx, commit1.short_id, commit2.idx, commit2.short_id))
76
77 response.mustcontain('<strong>{}</strong>'.format(f_path))
78
79 def test_diff_side_by_side_with_empty_file(self, app, backend, backend_stub):
80 commits = [
81 {'message': 'First commit'},
82 {'message': 'Commit with binary',
83 'added': [nodes.FileNode('file.empty', content='')]},
84 ]
85 f_path = 'file.empty'
86 repo = backend.create_repo(commits=commits)
87 commit1 = repo.get_commit(commit_idx=0)
88 commit2 = repo.get_commit(commit_idx=1)
89
90 response = self.app.get(route_path(
91 'repo_compare',
92 repo_name=repo.repo_name,
93 source_ref_type='rev',
94 source_ref=commit1.raw_id,
95 target_ref_type='rev',
96 target_ref=commit2.raw_id,
97 params=dict(f_path=f_path, target_repo=repo.repo_name, diffmode='sidebyside')
98 ))
99
100 response.mustcontain('Expand 1 commit')
101 response.mustcontain('1 file changed')
102
103 response.mustcontain(
104 'r%s:%s...r%s:%s' % (
105 commit1.idx, commit1.short_id, commit2.idx, commit2.short_id))
106
107 response.mustcontain('<strong>{}</strong>'.format(f_path))
108
109 def test_diff_sidebyside_two_commits(self, app, backend):
47 def test_diff_sidebyside_single_commit(self, app, backend):
110 48 commit_id_range = {
111 49 'hg': {
112 50 'commits': ['25d7e49c18b159446cadfa506a5cf8ad1cb04067',
@@ -141,26 +79,164 b' class TestSideBySideDiff(object):'
141 79 params=dict(target_repo=backend.repo_name, diffmode='sidebyside')
142 80 ))
143 81
82 response.mustcontain(file_changes)
144 83 response.mustcontain('Expand 1 commit')
145 response.mustcontain(file_changes)
146 84
147 def test_diff_sidebyside_two_commits_single_file(self, app, backend):
85 def test_diff_sidebyside_two_commits(self, app, backend):
148 86 commit_id_range = {
149 87 'hg': {
150 'commits': ['25d7e49c18b159446cadfa506a5cf8ad1cb04067',
88 'commits': ['4fdd71e9427417b2e904e0464c634fdee85ec5a7',
151 89 '603d6c72c46d953420c89d36372f08d9f305f5dd'],
152 'changes': '1 file changed: 1 inserted, 1 deleted'
90 'changes': '32 files changed: 1165 inserted, 308 deleted'
153 91 },
154 92 'git': {
155 'commits': ['6fc9270775aaf5544c1deb014f4ddd60c952fcbb',
93 'commits': ['f5fbf9cfd5f1f1be146f6d3b38bcd791a7480c13',
156 94 '03fa803d7e9fb14daa9a3089e0d1494eda75d986'],
157 'changes': '1 file changed: 1 inserted, 1 deleted'
95 'changes': '32 files changed: 1165 inserted, 308 deleted'
158 96 },
159 97
160 98 'svn': {
161 'commits': ['336',
99 'commits': ['335',
162 100 '337'],
163 'changes': '1 file changed: 1 inserted, 1 deleted'
101 'changes': '32 files changed: 1179 inserted, 310 deleted'
102 },
103 }
104
105 commit_info = commit_id_range[backend.alias]
106 commit2, commit1 = commit_info['commits']
107 file_changes = commit_info['changes']
108
109 response = self.app.get(route_path(
110 'repo_compare',
111 repo_name=backend.repo_name,
112 source_ref_type='rev',
113 source_ref=commit2,
114 target_repo=backend.repo_name,
115 target_ref_type='rev',
116 target_ref=commit1,
117 params=dict(target_repo=backend.repo_name, diffmode='sidebyside')
118 ))
119
120 response.mustcontain(file_changes)
121 response.mustcontain('Expand 2 commits')
122
123 @pytest.mark.xfail(reason='GIT does not handle empty commit compare correct (missing 1 commit)')
124 def test_diff_side_by_side_from_0_commit(self, app, backend, backend_stub):
125 f_path = 'test_sidebyside_file.py'
126 commit1_content = 'content-25d7e49c18b159446c\n'
127 commit2_content = 'content-603d6c72c46d953420\n'
128 repo = backend.create_repo()
129
130 commit1 = commit_change(
131 repo.repo_name, filename=f_path, content=commit1_content,
132 message='A', vcs_type=backend.alias, parent=None, newfile=True)
133
134 commit2 = commit_change(
135 repo.repo_name, filename=f_path, content=commit2_content,
136 message='B, child of A', vcs_type=backend.alias, parent=commit1)
137
138 response = self.app.get(route_path(
139 'repo_compare',
140 repo_name=repo.repo_name,
141 source_ref_type='rev',
142 source_ref=EmptyCommit().raw_id,
143 target_ref_type='rev',
144 target_ref=commit2.raw_id,
145 params=dict(diffmode='sidebyside')
146 ))
147
148 response.mustcontain('Expand 2 commits')
149 response.mustcontain('123 file changed')
150
151 response.mustcontain(
152 'r%s:%s...r%s:%s' % (
153 commit1.idx, commit1.short_id, commit2.idx, commit2.short_id))
154
155 response.mustcontain('<strong>{}</strong>'.format(f_path))
156
157 @pytest.mark.xfail(reason='GIT does not handle empty commit compare correct (missing 1 commit)')
158 def test_diff_side_by_side_from_0_commit_with_file_filter(self, app, backend, backend_stub):
159 f_path = 'test_sidebyside_file.py'
160 commit1_content = 'content-25d7e49c18b159446c\n'
161 commit2_content = 'content-603d6c72c46d953420\n'
162 repo = backend.create_repo()
163
164 commit1 = commit_change(
165 repo.repo_name, filename=f_path, content=commit1_content,
166 message='A', vcs_type=backend.alias, parent=None, newfile=True)
167
168 commit2 = commit_change(
169 repo.repo_name, filename=f_path, content=commit2_content,
170 message='B, child of A', vcs_type=backend.alias, parent=commit1)
171
172 response = self.app.get(route_path(
173 'repo_compare',
174 repo_name=repo.repo_name,
175 source_ref_type='rev',
176 source_ref=EmptyCommit().raw_id,
177 target_ref_type='rev',
178 target_ref=commit2.raw_id,
179 params=dict(f_path=f_path, target_repo=repo.repo_name, diffmode='sidebyside')
180 ))
181
182 response.mustcontain('Expand 2 commits')
183 response.mustcontain('1 file changed')
184
185 response.mustcontain(
186 'r%s:%s...r%s:%s' % (
187 commit1.idx, commit1.short_id, commit2.idx, commit2.short_id))
188
189 response.mustcontain('<strong>{}</strong>'.format(f_path))
190
191 def test_diff_side_by_side_with_empty_file(self, app, backend, backend_stub):
192 commits = [
193 {'message': 'First commit'},
194 {'message': 'Second commit'},
195 {'message': 'Commit with binary',
196 'added': [nodes.FileNode('file.empty', content='')]},
197 ]
198 f_path = 'file.empty'
199 repo = backend.create_repo(commits=commits)
200 commit1 = repo.get_commit(commit_idx=0)
201 commit2 = repo.get_commit(commit_idx=1)
202 commit3 = repo.get_commit(commit_idx=2)
203
204 response = self.app.get(route_path(
205 'repo_compare',
206 repo_name=repo.repo_name,
207 source_ref_type='rev',
208 source_ref=commit1.raw_id,
209 target_ref_type='rev',
210 target_ref=commit3.raw_id,
211 params=dict(f_path=f_path, target_repo=repo.repo_name, diffmode='sidebyside')
212 ))
213
214 response.mustcontain('Expand 2 commits')
215 response.mustcontain('1 file changed')
216
217 response.mustcontain(
218 'r%s:%s...r%s:%s' % (
219 commit2.idx, commit2.short_id, commit3.idx, commit3.short_id))
220
221 response.mustcontain('<strong>{}</strong>'.format(f_path))
222
223 def test_diff_sidebyside_two_commits_with_file_filter(self, app, backend):
224 commit_id_range = {
225 'hg': {
226 'commits': ['4fdd71e9427417b2e904e0464c634fdee85ec5a7',
227 '603d6c72c46d953420c89d36372f08d9f305f5dd'],
228 'changes': '1 file changed: 3 inserted, 3 deleted'
229 },
230 'git': {
231 'commits': ['f5fbf9cfd5f1f1be146f6d3b38bcd791a7480c13',
232 '03fa803d7e9fb14daa9a3089e0d1494eda75d986'],
233 'changes': '1 file changed: 3 inserted, 3 deleted'
234 },
235
236 'svn': {
237 'commits': ['335',
238 '337'],
239 'changes': '1 file changed: 3 inserted, 3 deleted'
164 240 },
165 241 }
166 242 f_path = 'docs/conf.py'
@@ -179,5 +255,5 b' class TestSideBySideDiff(object):'
179 255 params=dict(f_path=f_path, target_repo=backend.repo_name, diffmode='sidebyside')
180 256 ))
181 257
182 response.mustcontain('Expand 1 commit')
258 response.mustcontain('Expand 2 commits')
183 259 response.mustcontain(file_changes)
@@ -243,7 +243,7 b' class TestFilesViews(object):'
243 243 repo_name=backend.repo_name,
244 244 commit_id=commit.raw_id, f_path='vcs/nodes.py'))
245 245
246 msgbox = """<div class="commit right-content">%s</div>"""
246 msgbox = """<div class="commit">%s</div>"""
247 247 response.mustcontain(msgbox % (commit.message, ))
248 248
249 249 assert_response = response.assert_response()
@@ -313,6 +313,7 b' class TestFilesViews(object):'
313 313
314 314 expected_data = json.loads(
315 315 fixture.load_resource('svn_node_history_branches.json'))
316
316 317 assert expected_data == response.json
317 318
318 319 def test_file_source_history_with_annotation(self, backend, xhr_header):
@@ -521,10 +522,10 b' class TestRepositoryArchival(object):'
521 522 def test_archival(self, backend):
522 523 backend.enable_downloads()
523 524 commit = backend.repo.get_commit(commit_idx=173)
524 for archive, info in settings.ARCHIVE_SPECS.items():
525 mime_type, arch_ext = info
526 short = commit.short_id + arch_ext
527 fname = commit.raw_id + arch_ext
525 for a_type, content_type, extension in settings.ARCHIVE_SPECS:
526
527 short = commit.short_id + extension
528 fname = commit.raw_id + extension
528 529 filename = '%s-%s' % (backend.repo_name, short)
529 530 response = self.app.get(
530 531 route_path('repo_archivefile',
@@ -534,7 +535,7 b' class TestRepositoryArchival(object):'
534 535 assert response.status == '200 OK'
535 536 headers = [
536 537 ('Content-Disposition', 'attachment; filename=%s' % filename),
537 ('Content-Type', '%s' % mime_type),
538 ('Content-Type', '%s' % content_type),
538 539 ]
539 540
540 541 for header in headers:
@@ -761,7 +762,7 b' class TestModifyFilesWithWebInterface(ob'
761 762
762 763 @pytest.mark.xfail_backends("svn", reason="Depends on online editing")
763 764 def test_add_file_into_repo_missing_content(self, backend, csrf_token):
764 repo = backend.create_repo()
765 backend.create_repo()
765 766 filename = 'init.py'
766 767 response = self.app.post(
767 768 route_path('repo_files_create_file',
@@ -770,26 +771,25 b' class TestModifyFilesWithWebInterface(ob'
770 771 params={
771 772 'content': "",
772 773 'filename': filename,
773 'location': "",
774 774 'csrf_token': csrf_token,
775 775 },
776 776 status=302)
777 assert_session_flash(response,
778 'Successfully committed new file `{}`'.format(
779 os.path.join(filename)))
777 expected_msg = 'Successfully committed new file `{}`'.format(os.path.join(filename))
778 assert_session_flash(response, expected_msg)
780 779
781 780 def test_add_file_into_repo_missing_filename(self, backend, csrf_token):
781 commit_id = backend.repo.get_commit().raw_id
782 782 response = self.app.post(
783 783 route_path('repo_files_create_file',
784 784 repo_name=backend.repo_name,
785 commit_id='tip', f_path='/'),
785 commit_id=commit_id, f_path='/'),
786 786 params={
787 787 'content': "foo",
788 788 'csrf_token': csrf_token,
789 789 },
790 790 status=302)
791 791
792 assert_session_flash(response, 'No filename')
792 assert_session_flash(response, 'No filename specified')
793 793
794 794 def test_add_file_into_repo_errors_and_no_commits(
795 795 self, backend, csrf_token):
@@ -806,7 +806,7 b' class TestModifyFilesWithWebInterface(ob'
806 806 },
807 807 status=302)
808 808
809 assert_session_flash(response, 'No filename')
809 assert_session_flash(response, 'No filename specified')
810 810
811 811 # Not allowed, redirect to the summary
812 812 redirected = response.follow()
@@ -817,52 +817,51 b' class TestModifyFilesWithWebInterface(ob'
817 817
818 818 assert redirected.request.path == summary_url
819 819
820 @pytest.mark.parametrize("location, filename", [
821 ('/abs', 'foo'),
822 ('../rel', 'foo'),
823 ('file/../foo', 'foo'),
820 @pytest.mark.parametrize("filename, clean_filename", [
821 ('/abs/foo', 'abs/foo'),
822 ('../rel/foo', 'rel/foo'),
823 ('file/../foo/foo', 'file/foo/foo'),
824 824 ])
825 def test_add_file_into_repo_bad_filenames(
826 self, location, filename, backend, csrf_token):
825 def test_add_file_into_repo_bad_filenames(self, filename, clean_filename, backend, csrf_token):
826 repo = backend.create_repo()
827 commit_id = repo.get_commit().raw_id
828
827 829 response = self.app.post(
828 830 route_path('repo_files_create_file',
829 repo_name=backend.repo_name,
830 commit_id='tip', f_path='/'),
831 repo_name=repo.repo_name,
832 commit_id=commit_id, f_path='/'),
831 833 params={
832 834 'content': "foo",
833 835 'filename': filename,
834 'location': location,
835 836 'csrf_token': csrf_token,
836 837 },
837 838 status=302)
838 839
839 assert_session_flash(
840 response,
841 'The location specified must be a relative path and must not '
842 'contain .. in the path')
840 expected_msg = 'Successfully committed new file `{}`'.format(clean_filename)
841 assert_session_flash(response, expected_msg)
843 842
844 @pytest.mark.parametrize("cnt, location, filename", [
845 (1, '', 'foo.txt'),
846 (2, 'dir', 'foo.rst'),
847 (3, 'rel/dir', 'foo.bar'),
843 @pytest.mark.parametrize("cnt, filename, content", [
844 (1, 'foo.txt', "Content"),
845 (2, 'dir/foo.rst', "Content"),
846 (3, 'dir/foo-second.rst', "Content"),
847 (4, 'rel/dir/foo.bar', "Content"),
848 848 ])
849 def test_add_file_into_repo(self, cnt, location, filename, backend,
850 csrf_token):
849 def test_add_file_into_empty_repo(self, cnt, filename, content, backend, csrf_token):
851 850 repo = backend.create_repo()
851 commit_id = repo.get_commit().raw_id
852 852 response = self.app.post(
853 853 route_path('repo_files_create_file',
854 854 repo_name=repo.repo_name,
855 commit_id='tip', f_path='/'),
855 commit_id=commit_id, f_path='/'),
856 856 params={
857 'content': "foo",
857 'content': content,
858 858 'filename': filename,
859 'location': location,
860 859 'csrf_token': csrf_token,
861 860 },
862 861 status=302)
863 assert_session_flash(response,
864 'Successfully committed new file `{}`'.format(
865 os.path.join(location, filename)))
862
863 expected_msg = 'Successfully committed new file `{}`'.format(filename)
864 assert_session_flash(response, expected_msg)
866 865
867 866 def test_edit_file_view(self, backend):
868 867 response = self.app.get(
@@ -884,8 +883,7 b' class TestModifyFilesWithWebInterface(ob'
884 883 f_path='vcs/nodes.py'),
885 884 status=302)
886 885 assert_session_flash(
887 response,
888 'You can only edit files with commit being a valid branch')
886 response, 'Cannot modify file. Given commit `tip` is not head of a branch.')
889 887
890 888 def test_edit_file_view_commit_changes(self, backend, csrf_token):
891 889 repo = backend.create_repo()
@@ -953,8 +951,7 b' class TestModifyFilesWithWebInterface(ob'
953 951 f_path='vcs/nodes.py'),
954 952 status=302)
955 953 assert_session_flash(
956 response,
957 'You can only delete files with commit being a valid branch')
954 response, 'Cannot modify file. Given commit `tip` is not head of a branch.')
958 955
959 956 def test_delete_file_view_commit_changes(self, backend, csrf_token):
960 957 repo = backend.create_repo()
@@ -992,7 +989,7 b' class TestFilesViewOtherCases(object):'
992 989 repo_file_add_url = route_path(
993 990 'repo_files_add_file',
994 991 repo_name=repo.repo_name,
995 commit_id=0, f_path='') + '#edit'
992 commit_id=0, f_path='')
996 993
997 994 assert_session_flash(
998 995 response,
@@ -1009,7 +1006,7 b' class TestFilesViewOtherCases(object):'
1009 1006 repo_file_add_url = route_path(
1010 1007 'repo_files_add_file',
1011 1008 repo_name=repo.repo_name,
1012 commit_id=0, f_path='') + '#edit'
1009 commit_id=0, f_path='')
1013 1010
1014 1011 response = self.app.get(
1015 1012 route_path('repo_files',
@@ -40,6 +40,8 b' def route_path(name, params=None, **kwar'
40 40 base_url = {
41 41 'repo_changelog': '/{repo_name}/changelog',
42 42 'repo_changelog_file': '/{repo_name}/changelog/{commit_id}/{f_path}',
43 'repo_commits': '/{repo_name}/commits',
44 'repo_commits_file': '/{repo_name}/commits/{commit_id}/{f_path}',
43 45 'pullrequest_show': '/{repo_name}/pull-request/{pull_request_id}',
44 46 'pullrequest_show_all': '/{repo_name}/pull-request',
45 47 'pullrequest_show_all_data': '/{repo_name}/pull-request-data',
@@ -998,11 +1000,11 b' class TestPullrequestsView(object):'
998 1000 assert len(target_children) == 1
999 1001
1000 1002 expected_origin_link = route_path(
1001 'repo_changelog',
1003 'repo_commits',
1002 1004 repo_name=pull_request.source_repo.scm_instance().name,
1003 1005 params=dict(branch='origin'))
1004 1006 expected_target_link = route_path(
1005 'repo_changelog',
1007 'repo_commits',
1006 1008 repo_name=pull_request.target_repo.scm_instance().name,
1007 1009 params=dict(branch='target'))
1008 1010 assert origin_children[0].attrib['href'] == expected_origin_link
@@ -350,11 +350,11 b' class TestCreateReferenceData(object):'
350 350 {
351 351 'children': [
352 352 {
353 'id': 'a', 'raw_id': 'a_id', 'text': 'a', 'type': 't1',
353 'id': 'a', 'idx': 0, 'raw_id': 'a_id', 'text': 'a', 'type': 't1',
354 354 'files_url': expected_files_url + 'a/?at=a',
355 355 },
356 356 {
357 'id': 'b', 'raw_id': 'b_id', 'text': 'b', 'type': 't1',
357 'id': 'b', 'idx': 0, 'raw_id': 'b_id', 'text': 'b', 'type': 't1',
358 358 'files_url': expected_files_url + 'b/?at=b',
359 359 }
360 360 ],
@@ -363,7 +363,7 b' class TestCreateReferenceData(object):'
363 363 {
364 364 'children': [
365 365 {
366 'id': 'c', 'raw_id': 'c_id', 'text': 'c', 'type': 't2',
366 'id': 'c', 'idx': 0, 'raw_id': 'c_id', 'text': 'c', 'type': 't2',
367 367 'files_url': expected_files_url + 'c/?at=c',
368 368 }
369 369 ],
@@ -385,12 +385,12 b' class TestCreateReferenceData(object):'
385 385 {
386 386 'children': [
387 387 {
388 'id': 'a@a_id', 'raw_id': 'a_id',
388 'id': 'a@a_id', 'idx': 0, 'raw_id': 'a_id',
389 389 'text': 'a', 'type': 't1',
390 390 'files_url': expected_files_url + 'a_id/a?at=a',
391 391 },
392 392 {
393 'id': 'b@b_id', 'raw_id': 'b_id',
393 'id': 'b@b_id', 'idx': 0, 'raw_id': 'b_id',
394 394 'text': 'b', 'type': 't1',
395 395 'files_url': expected_files_url + 'b_id/b?at=b',
396 396 }
@@ -400,7 +400,7 b' class TestCreateReferenceData(object):'
400 400 {
401 401 'children': [
402 402 {
403 'id': 'c@c_id', 'raw_id': 'c_id',
403 'id': 'c@c_id', 'idx': 0, 'raw_id': 'c_id',
404 404 'text': 'c', 'type': 't2',
405 405 'files_url': expected_files_url + 'c_id/c?at=c',
406 406 }
@@ -516,6 +516,7 b' class TestReferenceItems(object):'
516 516 'text': ref_name,
517 517 'id': self._format_function(ref_name, ref_id),
518 518 'raw_id': ref_id,
519 'idx': 0,
519 520 'type': self.ref_type,
520 521 'files_url': self.fake_url
521 522 }
@@ -113,7 +113,7 b' class RepoChangelogView(RepoAppView):'
113 113 h.flash('Branch {} is not found.'.format(h.escape(branch_name)),
114 114 category='warning')
115 115 redirect_url = h.route_path(
116 'repo_changelog_file', repo_name=repo_name,
116 'repo_commits_file', repo_name=repo_name,
117 117 commit_id=branch_name, f_path=f_path or '')
118 118 raise HTTPFound(redirect_url)
119 119
@@ -127,13 +127,13 b' class RepoChangelogView(RepoAppView):'
127 127 if f_path:
128 128 # changelog for file
129 129 return h.route_path(
130 'repo_changelog_file',
130 'repo_commits_file',
131 131 repo_name=c.rhodecode_db_repo.repo_name,
132 132 commit_id=commit_id, f_path=f_path,
133 133 _query=query_params)
134 134 else:
135 135 return h.route_path(
136 'repo_changelog',
136 'repo_commits',
137 137 repo_name=c.rhodecode_db_repo.repo_name, _query=query_params)
138 138
139 139 c.total_cs = len(collection)
@@ -171,11 +171,18 b' class RepoChangelogView(RepoAppView):'
171 171 @HasRepoPermissionAnyDecorator(
172 172 'repository.read', 'repository.write', 'repository.admin')
173 173 @view_config(
174 route_name='repo_commits', request_method='GET',
175 renderer='rhodecode:templates/commits/changelog.mako')
176 @view_config(
177 route_name='repo_commits_file', request_method='GET',
178 renderer='rhodecode:templates/commits/changelog.mako')
179 # old routes for backward compat
180 @view_config(
174 181 route_name='repo_changelog', request_method='GET',
175 renderer='rhodecode:templates/changelog/changelog.mako')
182 renderer='rhodecode:templates/commits/changelog.mako')
176 183 @view_config(
177 184 route_name='repo_changelog_file', request_method='GET',
178 renderer='rhodecode:templates/changelog/changelog.mako')
185 renderer='rhodecode:templates/commits/changelog.mako')
179 186 def repo_changelog(self):
180 187 c = self.load_default_context()
181 188
@@ -224,7 +231,7 b' class RepoChangelogView(RepoAppView):'
224 231 except RepositoryError as e:
225 232 h.flash(safe_str(e), category='warning')
226 233 redirect_url = h.route_path(
227 'repo_changelog', repo_name=self.db_repo_name)
234 'repo_commits', repo_name=self.db_repo_name)
228 235 raise HTTPFound(redirect_url)
229 236 collection = list(reversed(collection))
230 237 else:
@@ -246,14 +253,14 b' class RepoChangelogView(RepoAppView):'
246 253 log.exception(safe_str(e))
247 254 h.flash(safe_str(h.escape(e)), category='error')
248 255 raise HTTPFound(
249 h.route_path('repo_changelog', repo_name=self.db_repo_name))
256 h.route_path('repo_commits', repo_name=self.db_repo_name))
250 257
251 258 if partial_xhr or self.request.environ.get('HTTP_X_PJAX'):
252 259 # case when loading dynamic file history in file view
253 260 # loading from ajax, we don't want the first result, it's popped
254 261 # in the code above
255 262 html = render(
256 'rhodecode:templates/changelog/changelog_file_history.mako',
263 'rhodecode:templates/commits/changelog_file_history.mako',
257 264 self._get_template_context(c), self.request)
258 265 return Response(html)
259 266
@@ -271,14 +278,14 b' class RepoChangelogView(RepoAppView):'
271 278 @HasRepoPermissionAnyDecorator(
272 279 'repository.read', 'repository.write', 'repository.admin')
273 280 @view_config(
274 route_name='repo_changelog_elements', request_method=('GET', 'POST'),
275 renderer='rhodecode:templates/changelog/changelog_elements.mako',
281 route_name='repo_commits_elements', request_method=('GET', 'POST'),
282 renderer='rhodecode:templates/commits/changelog_elements.mako',
276 283 xhr=True)
277 284 @view_config(
278 route_name='repo_changelog_elements_file', request_method=('GET', 'POST'),
279 renderer='rhodecode:templates/changelog/changelog_elements.mako',
285 route_name='repo_commits_elements_file', request_method=('GET', 'POST'),
286 renderer='rhodecode:templates/commits/changelog_elements.mako',
280 287 xhr=True)
281 def repo_changelog_elements(self):
288 def repo_commits_elements(self):
282 289 c = self.load_default_context()
283 290 commit_id = self.request.matchdict.get('commit_id')
284 291 f_path = self._get_f_path(self.request.matchdict)
@@ -312,7 +319,7 b' class RepoChangelogView(RepoAppView):'
312 319 except (RepositoryError, CommitDoesNotExistError, Exception) as e:
313 320 log.exception(safe_str(e))
314 321 raise HTTPFound(
315 h.route_path('repo_changelog', repo_name=self.db_repo_name))
322 h.route_path('repo_commits', repo_name=self.db_repo_name))
316 323
317 324 collection = base_commit.get_path_history(
318 325 f_path, limit=hist_limit, pre_load=pre_load)
@@ -105,10 +105,9 b' class RepoCommitsView(RepoAppView):'
105 105
106 106 c.commit_ranges = commits
107 107 if not c.commit_ranges:
108 raise RepositoryError(
109 'The commit range returned an empty result')
110 except CommitDoesNotExistError:
111 msg = _('No such commit exists for this repository')
108 raise RepositoryError('The commit range returned an empty result')
109 except CommitDoesNotExistError as e:
110 msg = _('No such commit exists. Org exception: `{}`').format(e)
112 111 h.flash(msg, category='error')
113 112 raise HTTPNotFound()
114 113 except Exception:
@@ -214,29 +214,23 b' class RepoCompareView(RepoAppView):'
214 214 pre_load = ["author", "branch", "date", "message"]
215 215 c.ancestor = None
216 216
217 if c.file_path:
218 if source_commit == target_commit:
219 c.commit_ranges = []
220 else:
221 c.commit_ranges = [target_commit]
222 else:
223 try:
224 c.commit_ranges = source_scm.compare(
225 source_commit.raw_id, target_commit.raw_id,
226 target_scm, merge, pre_load=pre_load)
227 if merge:
228 c.ancestor = source_scm.get_common_ancestor(
229 source_commit.raw_id, target_commit.raw_id, target_scm)
230 except RepositoryRequirementError:
231 msg = _('Could not compare repos with different '
232 'large file settings')
233 log.error(msg)
234 if partial:
235 return Response(msg)
236 h.flash(msg, category='error')
237 raise HTTPFound(
238 h.route_path('repo_compare_select',
239 repo_name=self.db_repo_name))
217 try:
218 c.commit_ranges = source_scm.compare(
219 source_commit.raw_id, target_commit.raw_id,
220 target_scm, merge, pre_load=pre_load) or []
221 if merge:
222 c.ancestor = source_scm.get_common_ancestor(
223 source_commit.raw_id, target_commit.raw_id, target_scm)
224 except RepositoryRequirementError:
225 msg = _('Could not compare repos with different '
226 'large file settings')
227 log.error(msg)
228 if partial:
229 return Response(msg)
230 h.flash(msg, category='error')
231 raise HTTPFound(
232 h.route_path('repo_compare_select',
233 repo_name=self.db_repo_name))
240 234
241 235 c.statuses = self.db_repo.statuses(
242 236 [x.raw_id for x in c.commit_ranges])
This diff has been collapsed as it changes many lines, (503 lines changed) Show them Hide them
@@ -25,6 +25,7 b' import shutil'
25 25 import tempfile
26 26 import collections
27 27 import urllib
28 import pathlib2
28 29
29 30 from pyramid.httpexceptions import HTTPNotFound, HTTPBadRequest, HTTPFound
30 31 from pyramid.view import view_config
@@ -42,7 +43,7 b' from rhodecode.lib.exceptions import Non'
42 43 from rhodecode.lib.codeblocks import (
43 44 filenode_as_lines_tokens, filenode_as_annotated_lines_tokens)
44 45 from rhodecode.lib.utils2 import (
45 convert_line_endings, detect_mode, safe_str, str2bool, safe_int)
46 convert_line_endings, detect_mode, safe_str, str2bool, safe_int, sha1, safe_unicode)
46 47 from rhodecode.lib.auth import (
47 48 LoginRequired, HasRepoPermissionAnyDecorator, CSRFRequired)
48 49 from rhodecode.lib.vcs import path as vcspath
@@ -87,7 +88,7 b' class RepoFilesView(RepoAppView):'
87 88 c.enable_downloads = self.db_repo.enable_downloads
88 89 return c
89 90
90 def _ensure_not_locked(self):
91 def _ensure_not_locked(self, commit_id='tip'):
91 92 _ = self.request.translate
92 93
93 94 repo = self.db_repo
@@ -98,21 +99,41 b' class RepoFilesView(RepoAppView):'
98 99 'warning')
99 100 files_url = h.route_path(
100 101 'repo_files:default_path',
101 repo_name=self.db_repo_name, commit_id='tip')
102 repo_name=self.db_repo_name, commit_id=commit_id)
102 103 raise HTTPFound(files_url)
103 104
104 def check_branch_permission(self, branch_name):
105 def forbid_non_head(self, is_head, f_path, commit_id='tip', json_mode=False):
106 _ = self.request.translate
107
108 if not is_head:
109 message = _('Cannot modify file. '
110 'Given commit `{}` is not head of a branch.').format(commit_id)
111 h.flash(message, category='warning')
112
113 if json_mode:
114 return message
115
116 files_url = h.route_path(
117 'repo_files', repo_name=self.db_repo_name, commit_id=commit_id,
118 f_path=f_path)
119 raise HTTPFound(files_url)
120
121 def check_branch_permission(self, branch_name, commit_id='tip', json_mode=False):
105 122 _ = self.request.translate
106 123
107 124 rule, branch_perm = self._rhodecode_user.get_rule_and_branch_permission(
108 125 self.db_repo_name, branch_name)
109 126 if branch_perm and branch_perm not in ['branch.push', 'branch.push_force']:
110 h.flash(
111 _('Branch `{}` changes forbidden by rule {}.').format(branch_name, rule),
112 'warning')
127 message = _('Branch `{}` changes forbidden by rule {}.').format(
128 branch_name, rule)
129 h.flash(message, 'warning')
130
131 if json_mode:
132 return message
133
113 134 files_url = h.route_path(
114 'repo_files:default_path',
115 repo_name=self.db_repo_name, commit_id='tip')
135 'repo_files:default_path', repo_name=self.db_repo_name, commit_id=commit_id)
136
116 137 raise HTTPFound(files_url)
117 138
118 139 def _get_commit_and_path(self):
@@ -146,8 +167,7 b' class RepoFilesView(RepoAppView):'
146 167
147 168 _url = h.route_path(
148 169 'repo_files_add_file',
149 repo_name=self.db_repo_name, commit_id=0, f_path='',
150 _anchor='edit')
170 repo_name=self.db_repo_name, commit_id=0, f_path='')
151 171
152 172 if h.HasRepoPermissionAny(
153 173 'repository.write', 'repository.admin')(self.db_repo_name):
@@ -185,8 +205,7 b' class RepoFilesView(RepoAppView):'
185 205 h.flash(_('No such commit exists for this repository'), category='error')
186 206 raise HTTPNotFound()
187 207 except RepositoryError as e:
188 log.warning('Repository error while fetching '
189 'filenode `%s`. Err:%s', path, e)
208 log.warning('Repository error while fetching filenode `%s`. Err:%s', path, e)
190 209 h.flash(safe_str(h.escape(e)), category='error')
191 210 raise HTTPNotFound()
192 211
@@ -195,12 +214,7 b' class RepoFilesView(RepoAppView):'
195 214 def _is_valid_head(self, commit_id, repo):
196 215 branch_name = sha_commit_id = ''
197 216 is_head = False
198
199 if h.is_svn(repo) and not repo.is_empty():
200 # Note: Subversion only has one head.
201 if commit_id == repo.get_commit(commit_idx=-1).raw_id:
202 is_head = True
203 return branch_name, sha_commit_id, is_head
217 log.debug('Checking if commit_id `%s` is a head for %s.', commit_id, repo)
204 218
205 219 for _branch_name, branch_commit_id in repo.branches.items():
206 220 # simple case we pass in branch name, it's a HEAD
@@ -216,8 +230,14 b' class RepoFilesView(RepoAppView):'
216 230 sha_commit_id = branch_commit_id
217 231 break
218 232
233 if h.is_svn(repo) and not repo.is_empty():
234 # Note: Subversion only has one head.
235 if commit_id == repo.get_commit(commit_idx=-1).raw_id:
236 is_head = True
237 return branch_name, sha_commit_id, is_head
238
219 239 # checked branches, means we only need to try to get the branch/commit_sha
220 if not repo.is_empty:
240 if not repo.is_empty():
221 241 commit = repo.get_commit(commit_id=commit_id)
222 242 if commit:
223 243 branch_name = commit.branch
@@ -225,8 +245,7 b' class RepoFilesView(RepoAppView):'
225 245
226 246 return branch_name, sha_commit_id, is_head
227 247
228 def _get_tree_at_commit(
229 self, c, commit_id, f_path, full_load=False):
248 def _get_tree_at_commit(self, c, commit_id, f_path, full_load=False):
230 249
231 250 repo_id = self.db_repo.repo_id
232 251 force_recache = self.get_recache_flag()
@@ -244,16 +263,16 b' class RepoFilesView(RepoAppView):'
244 263
245 264 @region.conditional_cache_on_arguments(namespace=cache_namespace_uid,
246 265 condition=cache_on)
247 def compute_file_tree(repo_id, commit_id, f_path, full_load):
248 log.debug('Generating cached file tree for repo_id: %s, %s, %s',
249 repo_id, commit_id, f_path)
266 def compute_file_tree(ver, repo_id, commit_id, f_path, full_load):
267 log.debug('Generating cached file tree at ver:%s for repo_id: %s, %s, %s',
268 ver, repo_id, commit_id, f_path)
250 269
251 270 c.full_load = full_load
252 271 return render(
253 272 'rhodecode:templates/files/files_browser_tree.mako',
254 273 self._get_template_context(c), self.request)
255 274
256 return compute_file_tree(self.db_repo.repo_id, commit_id, f_path, full_load)
275 return compute_file_tree('v1', self.db_repo.repo_id, commit_id, f_path, full_load)
257 276
258 277 def _get_archive_spec(self, fname):
259 278 log.debug('Detecting archive spec for: `%s`', fname)
@@ -261,8 +280,7 b' class RepoFilesView(RepoAppView):'
261 280 fileformat = None
262 281 ext = None
263 282 content_type = None
264 for a_type, ext_data in settings.ARCHIVE_SPECS.items():
265 content_type, extension = ext_data
283 for a_type, content_type, extension in settings.ARCHIVE_SPECS:
266 284
267 285 if fname.endswith(extension):
268 286 fileformat = a_type
@@ -278,6 +296,15 b' class RepoFilesView(RepoAppView):'
278 296
279 297 return commit_id, ext, fileformat, content_type
280 298
299 def create_pure_path(self, *parts):
300 # Split paths and sanitize them, removing any ../ etc
301 sanitized_path = [
302 x for x in pathlib2.PurePath(*parts).parts
303 if x not in ['.', '..']]
304
305 pure_path = pathlib2.PurePath(*sanitized_path)
306 return pure_path
307
281 308 @LoginRequired()
282 309 @HasRepoPermissionAnyDecorator(
283 310 'repository.read', 'repository.write', 'repository.admin')
@@ -289,9 +316,10 b' class RepoFilesView(RepoAppView):'
289 316 from rhodecode import CONFIG
290 317 _ = self.request.translate
291 318 self.load_default_context()
292
319 default_at_path = '/'
293 320 fname = self.request.matchdict['fname']
294 321 subrepos = self.request.GET.get('subrepos') == 'true'
322 at_path = self.request.GET.get('at_path') or default_at_path
295 323
296 324 if not self.db_repo.enable_downloads:
297 325 return Response(_('Downloads disabled'))
@@ -311,10 +339,31 b' class RepoFilesView(RepoAppView):'
311 339 except EmptyRepositoryError:
312 340 return Response(_('Empty repository'))
313 341
314 archive_name = '%s-%s%s%s' % (
315 safe_str(self.db_repo_name.replace('/', '_')),
316 '-sub' if subrepos else '',
317 safe_str(commit.short_id), ext)
342 try:
343 at_path = commit.get_node(at_path).path or default_at_path
344 except Exception:
345 return Response(_('No node at path {} for this repository').format(at_path))
346
347 path_sha = sha1(at_path)[:8]
348
349 # original backward compat name of archive
350 clean_name = safe_str(self.db_repo_name.replace('/', '_'))
351 short_sha = safe_str(commit.short_id)
352
353 if at_path == default_at_path:
354 archive_name = '{}-{}{}{}'.format(
355 clean_name,
356 '-sub' if subrepos else '',
357 short_sha,
358 ext)
359 # custom path and new name
360 else:
361 archive_name = '{}-{}{}-{}{}'.format(
362 clean_name,
363 '-sub' if subrepos else '',
364 short_sha,
365 path_sha,
366 ext)
318 367
319 368 use_cached_archive = False
320 369 archive_cache_enabled = CONFIG.get(
@@ -339,7 +388,8 b' class RepoFilesView(RepoAppView):'
339 388 fd, archive = tempfile.mkstemp()
340 389 log.debug('Creating new temp archive in %s', archive)
341 390 try:
342 commit.archive_repo(archive, kind=fileformat, subrepos=subrepos)
391 commit.archive_repo(archive, kind=fileformat, subrepos=subrepos,
392 archive_at_path=at_path)
343 393 except ImproperArchiveTypeError:
344 394 return _('Unknown archive type')
345 395 if archive_cache_enabled:
@@ -632,8 +682,7 b' class RepoFilesView(RepoAppView):'
632 682 c.authors = []
633 683 # this loads a simple tree without metadata to speed things up
634 684 # later via ajax we call repo_nodetree_full and fetch whole
635 c.file_tree = self._get_tree_at_commit(
636 c, c.commit.raw_id, f_path)
685 c.file_tree = self._get_tree_at_commit(c, c.commit.raw_id, f_path)
637 686
638 687 except RepositoryError as e:
639 688 h.flash(safe_str(h.escape(e)), category='error')
@@ -875,18 +924,17 b' class RepoFilesView(RepoAppView):'
875 924 self.db_repo_name, self.db_repo.repo_id, commit.raw_id, f_path)
876 925 return {'nodes': metadata}
877 926
878 def _create_references(
879 self, branches_or_tags, symbolic_reference, f_path):
927 def _create_references(self, branches_or_tags, symbolic_reference, f_path, ref_type):
880 928 items = []
881 929 for name, commit_id in branches_or_tags.items():
882 sym_ref = symbolic_reference(commit_id, name, f_path)
883 items.append((sym_ref, name))
930 sym_ref = symbolic_reference(commit_id, name, f_path, ref_type)
931 items.append((sym_ref, name, ref_type))
884 932 return items
885 933
886 def _symbolic_reference(self, commit_id, name, f_path):
934 def _symbolic_reference(self, commit_id, name, f_path, ref_type):
887 935 return commit_id
888 936
889 def _symbolic_reference_svn(self, commit_id, name, f_path):
937 def _symbolic_reference_svn(self, commit_id, name, f_path, ref_type):
890 938 new_f_path = vcspath.join(name, f_path)
891 939 return u'%s@%s' % (new_f_path, commit_id)
892 940
@@ -916,7 +964,7 b' class RepoFilesView(RepoAppView):'
916 964 for commit in commits:
917 965 branch = ' (%s)' % commit.branch if commit.branch else ''
918 966 n_desc = 'r%s:%s%s' % (commit.idx, commit.short_id, branch)
919 commits_group[0].append((commit.raw_id, n_desc,))
967 commits_group[0].append((commit.raw_id, n_desc, 'sha'))
920 968 history.append(commits_group)
921 969
922 970 symbolic_reference = self._symbolic_reference
@@ -932,11 +980,11 b' class RepoFilesView(RepoAppView):'
932 980 symbolic_reference = self._symbolic_reference_svn
933 981
934 982 branches = self._create_references(
935 self.rhodecode_vcs_repo.branches, symbolic_reference, f_path)
983 self.rhodecode_vcs_repo.branches, symbolic_reference, f_path, 'branch')
936 984 branches_group = (branches, _("Branches"))
937 985
938 986 tags = self._create_references(
939 self.rhodecode_vcs_repo.tags, symbolic_reference, f_path)
987 self.rhodecode_vcs_repo.tags, symbolic_reference, f_path, 'tag')
940 988 tags_group = (tags, _("Tags"))
941 989
942 990 history.append(branches_group)
@@ -964,7 +1012,7 b' class RepoFilesView(RepoAppView):'
964 1012 for obj in file_history:
965 1013 res.append({
966 1014 'text': obj[1],
967 'children': [{'id': o[0], 'text': o[1]} for o in obj[0]]
1015 'children': [{'id': o[0], 'text': o[1], 'type': o[2]} for o in obj[0]]
968 1016 })
969 1017
970 1018 data = {
@@ -1035,15 +1083,9 b' class RepoFilesView(RepoAppView):'
1035 1083 _branch_name, _sha_commit_id, is_head = \
1036 1084 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1037 1085
1038 if not is_head:
1039 h.flash(_('You can only delete files with commit '
1040 'being a valid branch head.'), category='warning')
1041 raise HTTPFound(
1042 h.route_path('repo_files',
1043 repo_name=self.db_repo_name, commit_id='tip',
1044 f_path=f_path))
1086 self.forbid_non_head(is_head, f_path)
1087 self.check_branch_permission(_branch_name)
1045 1088
1046 self.check_branch_permission(_branch_name)
1047 1089 c.commit = self._get_commit_or_redirect(commit_id)
1048 1090 c.file = self._get_filenode_or_redirect(c.commit, f_path)
1049 1091
@@ -1069,13 +1111,7 b' class RepoFilesView(RepoAppView):'
1069 1111 _branch_name, _sha_commit_id, is_head = \
1070 1112 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1071 1113
1072 if not is_head:
1073 h.flash(_('You can only delete files with commit '
1074 'being a valid branch head.'), category='warning')
1075 raise HTTPFound(
1076 h.route_path('repo_files',
1077 repo_name=self.db_repo_name, commit_id='tip',
1078 f_path=f_path))
1114 self.forbid_non_head(is_head, f_path)
1079 1115 self.check_branch_permission(_branch_name)
1080 1116
1081 1117 c.commit = self._get_commit_or_redirect(commit_id)
@@ -1125,14 +1161,8 b' class RepoFilesView(RepoAppView):'
1125 1161 _branch_name, _sha_commit_id, is_head = \
1126 1162 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1127 1163
1128 if not is_head:
1129 h.flash(_('You can only edit files with commit '
1130 'being a valid branch head.'), category='warning')
1131 raise HTTPFound(
1132 h.route_path('repo_files',
1133 repo_name=self.db_repo_name, commit_id='tip',
1134 f_path=f_path))
1135 self.check_branch_permission(_branch_name)
1164 self.forbid_non_head(is_head, f_path, commit_id=commit_id)
1165 self.check_branch_permission(_branch_name, commit_id=commit_id)
1136 1166
1137 1167 c.commit = self._get_commit_or_redirect(commit_id)
1138 1168 c.file = self._get_filenode_or_redirect(c.commit, f_path)
@@ -1144,8 +1174,7 b' class RepoFilesView(RepoAppView):'
1144 1174 commit_id=c.commit.raw_id, f_path=f_path)
1145 1175 raise HTTPFound(files_url)
1146 1176
1147 c.default_message = _(
1148 'Edited file {} via RhodeCode Enterprise').format(f_path)
1177 c.default_message = _('Edited file {} via RhodeCode Enterprise').format(f_path)
1149 1178 c.f_path = f_path
1150 1179
1151 1180 return self._get_template_context(c)
@@ -1162,32 +1191,23 b' class RepoFilesView(RepoAppView):'
1162 1191 commit_id, f_path = self._get_commit_and_path()
1163 1192
1164 1193 self._ensure_not_locked()
1165 _branch_name, _sha_commit_id, is_head = \
1166 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1167
1168 if not is_head:
1169 h.flash(_('You can only edit files with commit '
1170 'being a valid branch head.'), category='warning')
1171 raise HTTPFound(
1172 h.route_path('repo_files',
1173 repo_name=self.db_repo_name, commit_id='tip',
1174 f_path=f_path))
1175
1176 self.check_branch_permission(_branch_name)
1177 1194
1178 1195 c.commit = self._get_commit_or_redirect(commit_id)
1179 1196 c.file = self._get_filenode_or_redirect(c.commit, f_path)
1180 1197
1181 1198 if c.file.is_binary:
1182 raise HTTPFound(
1183 h.route_path('repo_files',
1184 repo_name=self.db_repo_name,
1185 commit_id=c.commit.raw_id,
1186 f_path=f_path))
1199 raise HTTPFound(h.route_path('repo_files', repo_name=self.db_repo_name,
1200 commit_id=c.commit.raw_id, f_path=f_path))
1201
1202 _branch_name, _sha_commit_id, is_head = \
1203 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1187 1204
1188 c.default_message = _(
1189 'Edited file {} via RhodeCode Enterprise').format(f_path)
1205 self.forbid_non_head(is_head, f_path, commit_id=commit_id)
1206 self.check_branch_permission(_branch_name, commit_id=commit_id)
1207
1208 c.default_message = _('Edited file {} via RhodeCode Enterprise').format(f_path)
1190 1209 c.f_path = f_path
1210
1191 1211 old_content = c.file.content
1192 1212 sl = old_content.splitlines(1)
1193 1213 first_line = sl[0] if sl else ''
@@ -1198,20 +1218,25 b' class RepoFilesView(RepoAppView):'
1198 1218 content = convert_line_endings(r_post.get('content', ''), line_ending_mode)
1199 1219
1200 1220 message = r_post.get('message') or c.default_message
1201 org_f_path = c.file.unicode_path
1221 org_node_path = c.file.unicode_path
1202 1222 filename = r_post['filename']
1203 org_filename = c.file.name
1223
1224 root_path = c.file.dir_path
1225 pure_path = self.create_pure_path(root_path, filename)
1226 node_path = safe_unicode(bytes(pure_path))
1204 1227
1205 if content == old_content and filename == org_filename:
1206 h.flash(_('No changes'), category='warning')
1207 raise HTTPFound(
1208 h.route_path('repo_commit', repo_name=self.db_repo_name,
1209 commit_id='tip'))
1228 default_redirect_url = h.route_path('repo_commit', repo_name=self.db_repo_name,
1229 commit_id=commit_id)
1230 if content == old_content and node_path == org_node_path:
1231 h.flash(_('No changes detected on {}').format(org_node_path),
1232 category='warning')
1233 raise HTTPFound(default_redirect_url)
1234
1210 1235 try:
1211 1236 mapping = {
1212 org_f_path: {
1213 'org_filename': org_f_path,
1214 'filename': os.path.join(c.file.dir_path, filename),
1237 org_node_path: {
1238 'org_filename': org_node_path,
1239 'filename': node_path,
1215 1240 'content': content,
1216 1241 'lexer': '',
1217 1242 'op': 'mod',
@@ -1219,7 +1244,7 b' class RepoFilesView(RepoAppView):'
1219 1244 }
1220 1245 }
1221 1246
1222 ScmModel().update_nodes(
1247 commit = ScmModel().update_nodes(
1223 1248 user=self._rhodecode_db_user.user_id,
1224 1249 repo=self.db_repo,
1225 1250 message=message,
@@ -1227,21 +1252,25 b' class RepoFilesView(RepoAppView):'
1227 1252 parent_commit=c.commit,
1228 1253 )
1229 1254
1230 h.flash(
1231 _('Successfully committed changes to file `{}`').format(
1255 h.flash(_('Successfully committed changes to file `{}`').format(
1232 1256 h.escape(f_path)), category='success')
1257 default_redirect_url = h.route_path(
1258 'repo_commit', repo_name=self.db_repo_name, commit_id=commit.raw_id)
1259
1233 1260 except Exception:
1234 1261 log.exception('Error occurred during commit')
1235 1262 h.flash(_('Error occurred during commit'), category='error')
1236 raise HTTPFound(
1237 h.route_path('repo_commit', repo_name=self.db_repo_name,
1238 commit_id='tip'))
1263
1264 raise HTTPFound(default_redirect_url)
1239 1265
1240 1266 @LoginRequired()
1241 1267 @HasRepoPermissionAnyDecorator('repository.write', 'repository.admin')
1242 1268 @view_config(
1243 1269 route_name='repo_files_add_file', request_method='GET',
1244 1270 renderer='rhodecode:templates/files/files_add.mako')
1271 @view_config(
1272 route_name='repo_files_upload_file', request_method='GET',
1273 renderer='rhodecode:templates/files/files_upload.mako')
1245 1274 def repo_files_add_file(self):
1246 1275 _ = self.request.translate
1247 1276 c = self.load_default_context()
@@ -1252,27 +1281,20 b' class RepoFilesView(RepoAppView):'
1252 1281 c.commit = self._get_commit_or_redirect(commit_id, redirect_after=False)
1253 1282 if c.commit is None:
1254 1283 c.commit = EmptyCommit(alias=self.rhodecode_vcs_repo.alias)
1255 c.default_message = (_('Added file via RhodeCode Enterprise'))
1256 c.f_path = f_path.lstrip('/') # ensure not relative path
1257 1284
1258 if self.rhodecode_vcs_repo.is_empty:
1285 if self.rhodecode_vcs_repo.is_empty():
1259 1286 # for empty repository we cannot check for current branch, we rely on
1260 1287 # c.commit.branch instead
1261 _branch_name = c.commit.branch
1262 is_head = True
1288 _branch_name, _sha_commit_id, is_head = c.commit.branch, '', True
1263 1289 else:
1264 1290 _branch_name, _sha_commit_id, is_head = \
1265 1291 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1266 1292
1267 if not is_head:
1268 h.flash(_('You can only add files with commit '
1269 'being a valid branch head.'), category='warning')
1270 raise HTTPFound(
1271 h.route_path('repo_files',
1272 repo_name=self.db_repo_name, commit_id='tip',
1273 f_path=f_path))
1293 self.forbid_non_head(is_head, f_path, commit_id=commit_id)
1294 self.check_branch_permission(_branch_name, commit_id=commit_id)
1274 1295
1275 self.check_branch_permission(_branch_name)
1296 c.default_message = (_('Added file via RhodeCode Enterprise'))
1297 c.f_path = f_path.lstrip('/') # ensure not relative path
1276 1298
1277 1299 return self._get_template_context(c)
1278 1300
@@ -1289,86 +1311,62 b' class RepoFilesView(RepoAppView):'
1289 1311
1290 1312 self._ensure_not_locked()
1291 1313
1292 r_post = self.request.POST
1293
1294 c.commit = self._get_commit_or_redirect(
1295 commit_id, redirect_after=False)
1314 c.commit = self._get_commit_or_redirect(commit_id, redirect_after=False)
1296 1315 if c.commit is None:
1297 1316 c.commit = EmptyCommit(alias=self.rhodecode_vcs_repo.alias)
1298 1317
1299 if self.rhodecode_vcs_repo.is_empty:
1300 # for empty repository we cannot check for current branch, we rely on
1301 # c.commit.branch instead
1302 _branch_name = c.commit.branch
1303 is_head = True
1304 else:
1305 _branch_name, _sha_commit_id, is_head = \
1306 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1307
1308 if not is_head:
1309 h.flash(_('You can only add files with commit '
1310 'being a valid branch head.'), category='warning')
1311 raise HTTPFound(
1312 h.route_path('repo_files',
1313 repo_name=self.db_repo_name, commit_id='tip',
1314 f_path=f_path))
1315
1316 self.check_branch_permission(_branch_name)
1317
1318 c.default_message = (_('Added file via RhodeCode Enterprise'))
1319 c.f_path = f_path
1320 unix_mode = 0
1321 content = convert_line_endings(r_post.get('content', ''), unix_mode)
1322
1323 message = r_post.get('message') or c.default_message
1324 filename = r_post.get('filename')
1325 location = r_post.get('location', '') # dir location
1326 file_obj = r_post.get('upload_file', None)
1327
1328 if file_obj is not None and hasattr(file_obj, 'filename'):
1329 filename = r_post.get('filename_upload')
1330 content = file_obj.file
1331
1332 if hasattr(content, 'file'):
1333 # non posix systems store real file under file attr
1334 content = content.file
1335
1336 if self.rhodecode_vcs_repo.is_empty:
1318 # calculate redirect URL
1319 if self.rhodecode_vcs_repo.is_empty():
1337 1320 default_redirect_url = h.route_path(
1338 1321 'repo_summary', repo_name=self.db_repo_name)
1339 1322 else:
1340 1323 default_redirect_url = h.route_path(
1341 1324 'repo_commit', repo_name=self.db_repo_name, commit_id='tip')
1342 1325
1343 # If there's no commit, redirect to repo summary
1344 if type(c.commit) is EmptyCommit:
1345 redirect_url = h.route_path(
1346 'repo_summary', repo_name=self.db_repo_name)
1326 if self.rhodecode_vcs_repo.is_empty():
1327 # for empty repository we cannot check for current branch, we rely on
1328 # c.commit.branch instead
1329 _branch_name, _sha_commit_id, is_head = c.commit.branch, '', True
1347 1330 else:
1348 redirect_url = default_redirect_url
1331 _branch_name, _sha_commit_id, is_head = \
1332 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1333
1334 self.forbid_non_head(is_head, f_path, commit_id=commit_id)
1335 self.check_branch_permission(_branch_name, commit_id=commit_id)
1336
1337 c.default_message = (_('Added file via RhodeCode Enterprise'))
1338 c.f_path = f_path
1339
1340 r_post = self.request.POST
1341 message = r_post.get('message') or c.default_message
1342 filename = r_post.get('filename')
1343 unix_mode = 0
1344 content = convert_line_endings(r_post.get('content', ''), unix_mode)
1349 1345
1350 1346 if not filename:
1351 h.flash(_('No filename'), category='warning')
1347 # If there's no commit, redirect to repo summary
1348 if type(c.commit) is EmptyCommit:
1349 redirect_url = h.route_path(
1350 'repo_summary', repo_name=self.db_repo_name)
1351 else:
1352 redirect_url = default_redirect_url
1353 h.flash(_('No filename specified'), category='warning')
1352 1354 raise HTTPFound(redirect_url)
1353 1355
1354 # extract the location from filename,
1355 # allows using foo/bar.txt syntax to create subdirectories
1356 subdir_loc = filename.rsplit('/', 1)
1357 if len(subdir_loc) == 2:
1358 location = os.path.join(location, subdir_loc[0])
1356 root_path = f_path
1357 pure_path = self.create_pure_path(root_path, filename)
1358 node_path = safe_unicode(bytes(pure_path).lstrip('/'))
1359 1359
1360 # strip all crap out of file, just leave the basename
1361 filename = os.path.basename(filename)
1362 node_path = os.path.join(location, filename)
1363 1360 author = self._rhodecode_db_user.full_contact
1361 nodes = {
1362 node_path: {
1363 'content': content
1364 }
1365 }
1364 1366
1365 1367 try:
1366 nodes = {
1367 node_path: {
1368 'content': content
1369 }
1370 }
1371 ScmModel().create_nodes(
1368
1369 commit = ScmModel().create_nodes(
1372 1370 user=self._rhodecode_db_user.user_id,
1373 1371 repo=self.db_repo,
1374 1372 message=message,
@@ -1377,14 +1375,16 b' class RepoFilesView(RepoAppView):'
1377 1375 author=author,
1378 1376 )
1379 1377
1380 h.flash(
1381 _('Successfully committed new file `{}`').format(
1378 h.flash(_('Successfully committed new file `{}`').format(
1382 1379 h.escape(node_path)), category='success')
1380
1381 default_redirect_url = h.route_path(
1382 'repo_commit', repo_name=self.db_repo_name, commit_id=commit.raw_id)
1383
1383 1384 except NonRelativePathError:
1384 1385 log.exception('Non Relative path found')
1385 h.flash(_(
1386 'The location specified must be a relative path and must not '
1387 'contain .. in the path'), category='warning')
1386 h.flash(_('The location specified must be a relative path and must not '
1387 'contain .. in the path'), category='warning')
1388 1388 raise HTTPFound(default_redirect_url)
1389 1389 except (NodeError, NodeAlreadyExistsError) as e:
1390 1390 h.flash(_(h.escape(e)), category='error')
@@ -1393,3 +1393,134 b' class RepoFilesView(RepoAppView):'
1393 1393 h.flash(_('Error occurred during commit'), category='error')
1394 1394
1395 1395 raise HTTPFound(default_redirect_url)
1396
1397 @LoginRequired()
1398 @HasRepoPermissionAnyDecorator('repository.write', 'repository.admin')
1399 @CSRFRequired()
1400 @view_config(
1401 route_name='repo_files_upload_file', request_method='POST',
1402 renderer='json_ext')
1403 def repo_files_upload_file(self):
1404 _ = self.request.translate
1405 c = self.load_default_context()
1406 commit_id, f_path = self._get_commit_and_path()
1407
1408 self._ensure_not_locked()
1409
1410 c.commit = self._get_commit_or_redirect(commit_id, redirect_after=False)
1411 if c.commit is None:
1412 c.commit = EmptyCommit(alias=self.rhodecode_vcs_repo.alias)
1413
1414 # calculate redirect URL
1415 if self.rhodecode_vcs_repo.is_empty():
1416 default_redirect_url = h.route_path(
1417 'repo_summary', repo_name=self.db_repo_name)
1418 else:
1419 default_redirect_url = h.route_path(
1420 'repo_commit', repo_name=self.db_repo_name, commit_id='tip')
1421
1422 if self.rhodecode_vcs_repo.is_empty():
1423 # for empty repository we cannot check for current branch, we rely on
1424 # c.commit.branch instead
1425 _branch_name, _sha_commit_id, is_head = c.commit.branch, '', True
1426 else:
1427 _branch_name, _sha_commit_id, is_head = \
1428 self._is_valid_head(commit_id, self.rhodecode_vcs_repo)
1429
1430 error = self.forbid_non_head(is_head, f_path, json_mode=True)
1431 if error:
1432 return {
1433 'error': error,
1434 'redirect_url': default_redirect_url
1435 }
1436 error = self.check_branch_permission(_branch_name, json_mode=True)
1437 if error:
1438 return {
1439 'error': error,
1440 'redirect_url': default_redirect_url
1441 }
1442
1443 c.default_message = (_('Uploaded file via RhodeCode Enterprise'))
1444 c.f_path = f_path
1445
1446 r_post = self.request.POST
1447
1448 message = c.default_message
1449 user_message = r_post.getall('message')
1450 if isinstance(user_message, list) and user_message:
1451 # we take the first from duplicated results if it's not empty
1452 message = user_message[0] if user_message[0] else message
1453
1454 nodes = {}
1455
1456 for file_obj in r_post.getall('files_upload') or []:
1457 content = file_obj.file
1458 filename = file_obj.filename
1459
1460 root_path = f_path
1461 pure_path = self.create_pure_path(root_path, filename)
1462 node_path = safe_unicode(bytes(pure_path).lstrip('/'))
1463
1464 nodes[node_path] = {
1465 'content': content
1466 }
1467
1468 if not nodes:
1469 error = 'missing files'
1470 return {
1471 'error': error,
1472 'redirect_url': default_redirect_url
1473 }
1474
1475 author = self._rhodecode_db_user.full_contact
1476
1477 try:
1478 commit = ScmModel().create_nodes(
1479 user=self._rhodecode_db_user.user_id,
1480 repo=self.db_repo,
1481 message=message,
1482 nodes=nodes,
1483 parent_commit=c.commit,
1484 author=author,
1485 )
1486 if len(nodes) == 1:
1487 flash_message = _('Successfully committed {} new files').format(len(nodes))
1488 else:
1489 flash_message = _('Successfully committed 1 new file')
1490
1491 h.flash(flash_message, category='success')
1492
1493 default_redirect_url = h.route_path(
1494 'repo_commit', repo_name=self.db_repo_name, commit_id=commit.raw_id)
1495
1496 except NonRelativePathError:
1497 log.exception('Non Relative path found')
1498 error = _('The location specified must be a relative path and must not '
1499 'contain .. in the path')
1500 h.flash(error, category='warning')
1501
1502 return {
1503 'error': error,
1504 'redirect_url': default_redirect_url
1505 }
1506 except (NodeError, NodeAlreadyExistsError) as e:
1507 error = h.escape(e)
1508 h.flash(error, category='error')
1509
1510 return {
1511 'error': error,
1512 'redirect_url': default_redirect_url
1513 }
1514 except Exception:
1515 log.exception('Error occurred during commit')
1516 error = _('Error occurred during commit')
1517 h.flash(error, category='error')
1518 return {
1519 'error': error,
1520 'redirect_url': default_redirect_url
1521 }
1522
1523 return {
1524 'error': None,
1525 'redirect_url': default_redirect_url
1526 }
@@ -72,6 +72,7 b' class RepoSummaryView(RepoAppView):'
72 72 log.debug("Searching for a README file.")
73 73 readme_node = ReadmeFinder(_renderer_type).search(commit)
74 74 if readme_node:
75 log.debug('Found README node: %s', readme_node)
75 76 relative_urls = {
76 77 'raw': h.route_path(
77 78 'repo_file_raw', repo_name=_repo_name,
@@ -82,7 +83,8 b' class RepoSummaryView(RepoAppView):'
82 83 }
83 84 readme_data = self._render_readme_or_none(
84 85 commit, readme_node, relative_urls)
85 readme_filename = readme_node.path
86 readme_filename = readme_node.unicode_path
87
86 88 return readme_data, readme_filename
87 89
88 90 inv_context_manager = rc_cache.InvalidationContext(
@@ -152,6 +154,26 b' class RepoSummaryView(RepoAppView):'
152 154 c.comments = self.db_repo.get_comments(page_ids)
153 155 c.statuses = self.db_repo.statuses(page_ids)
154 156
157 def _prepare_and_set_clone_url(self, c):
158 username = ''
159 if self._rhodecode_user.username != User.DEFAULT_USER:
160 username = safe_str(self._rhodecode_user.username)
161
162 _def_clone_uri = _def_clone_uri_id = c.clone_uri_tmpl
163 _def_clone_uri_ssh = c.clone_uri_ssh_tmpl
164
165 if '{repo}' in _def_clone_uri:
166 _def_clone_uri_id = _def_clone_uri.replace('{repo}', '_{repoid}')
167 elif '{repoid}' in _def_clone_uri:
168 _def_clone_uri_id = _def_clone_uri.replace('_{repoid}', '{repo}')
169
170 c.clone_repo_url = self.db_repo.clone_url(
171 user=username, uri_tmpl=_def_clone_uri)
172 c.clone_repo_url_id = self.db_repo.clone_url(
173 user=username, uri_tmpl=_def_clone_uri_id)
174 c.clone_repo_url_ssh = self.db_repo.clone_url(
175 uri_tmpl=_def_clone_uri_ssh, ssh=True)
176
155 177 @LoginRequired()
156 178 @HasRepoPermissionAnyDecorator(
157 179 'repository.read', 'repository.write', 'repository.admin')
@@ -160,6 +182,7 b' class RepoSummaryView(RepoAppView):'
160 182 renderer='rhodecode:templates/summary/summary_commits.mako')
161 183 def summary_commits(self):
162 184 c = self.load_default_context()
185 self._prepare_and_set_clone_url(c)
163 186 self._load_commits_context(c)
164 187 return self._get_template_context(c)
165 188
@@ -179,26 +202,11 b' class RepoSummaryView(RepoAppView):'
179 202 c = self.load_default_context()
180 203
181 204 # Prepare the clone URL
182 username = ''
183 if self._rhodecode_user.username != User.DEFAULT_USER:
184 username = safe_str(self._rhodecode_user.username)
185
186 _def_clone_uri = _def_clone_uri_id = c.clone_uri_tmpl
187 _def_clone_uri_ssh = c.clone_uri_ssh_tmpl
205 self._prepare_and_set_clone_url(c)
188 206
189 if '{repo}' in _def_clone_uri:
190 _def_clone_uri_id = _def_clone_uri.replace(
191 '{repo}', '_{repoid}')
192 elif '{repoid}' in _def_clone_uri:
193 _def_clone_uri_id = _def_clone_uri.replace(
194 '_{repoid}', '{repo}')
195
196 c.clone_repo_url = self.db_repo.clone_url(
197 user=username, uri_tmpl=_def_clone_uri)
198 c.clone_repo_url_id = self.db_repo.clone_url(
199 user=username, uri_tmpl=_def_clone_uri_id)
200 c.clone_repo_url_ssh = self.db_repo.clone_url(
201 uri_tmpl=_def_clone_uri_ssh, ssh=True)
207 # update every 5 min
208 if self.db_repo.last_commit_cache_update_diff > 60 * 5:
209 self.db_repo.update_commit_cache()
202 210
203 211 # If enabled, get statistics data
204 212
@@ -231,8 +239,6 b' class RepoSummaryView(RepoAppView):'
231 239 c.enable_downloads = self.db_repo.enable_downloads
232 240 c.repository_followers = scm_model.get_followers(self.db_repo)
233 241 c.repository_forks = scm_model.get_forks(self.db_repo)
234 c.repository_is_user_following = scm_model.is_following_repo(
235 self.db_repo_name, self._rhodecode_user.user_id)
236 242
237 243 # first interaction with the VCS instance after here...
238 244 if c.repository_requirements_missing:
@@ -317,8 +323,7 b' class RepoSummaryView(RepoAppView):'
317 323 (_("Tag"), repo.tags, 'tag'),
318 324 (_("Bookmark"), repo.bookmarks, 'book'),
319 325 ]
320 res = self._create_reference_data(
321 repo, self.db_repo_name, refs_to_create)
326 res = self._create_reference_data(repo, self.db_repo_name, refs_to_create)
322 327 data = {
323 328 'more': False,
324 329 'results': res
@@ -365,8 +370,7 b' class RepoSummaryView(RepoAppView):'
365 370 })
366 371 return result
367 372
368 def _create_reference_items(self, repo, full_repo_name, refs, ref_type,
369 format_ref_id):
373 def _create_reference_items(self, repo, full_repo_name, refs, ref_type, format_ref_id):
370 374 result = []
371 375 is_svn = h.is_svn(repo)
372 376 for ref_name, raw_id in refs.iteritems():
@@ -378,6 +382,7 b' class RepoSummaryView(RepoAppView):'
378 382 'raw_id': raw_id,
379 383 'type': ref_type,
380 384 'files_url': files_url,
385 'idx': 0,
381 386 })
382 387 return result
383 388
@@ -20,12 +20,13 b''
20 20
21 21 import os
22 22 import sys
23 import shutil
24 23 import logging
25 24 import tempfile
26 25 import textwrap
27
26 import collections
28 27 from .base import VcsServer
28 from rhodecode.model.db import RhodeCodeUi
29 from rhodecode.model.settings import VcsSettingsModel
29 30
30 31 log = logging.getLogger(__name__)
31 32
@@ -37,62 +38,46 b' class MercurialTunnelWrapper(object):'
37 38 self.server = server
38 39 self.stdin = sys.stdin
39 40 self.stdout = sys.stdout
40 self.svn_conf_fd, self.svn_conf_path = tempfile.mkstemp()
41 self.hooks_env_fd, self.hooks_env_path = tempfile.mkstemp()
41 self.hooks_env_fd, self.hooks_env_path = tempfile.mkstemp(prefix='hgrc_rhodecode_')
42 42
43 43 def create_hooks_env(self):
44 repo_name = self.server.repo_name
45 hg_flags = self.server.config_to_hgrc(repo_name)
44 46
45 47 content = textwrap.dedent(
46 48 '''
47 # SSH hooks version=1.0.0
48 [hooks]
49 pretxnchangegroup.ssh_auth=python:vcsserver.hooks.pre_push_ssh_auth
50 pretxnchangegroup.ssh=python:vcsserver.hooks.pre_push_ssh
51 changegroup.ssh=python:vcsserver.hooks.post_push_ssh
52
53 preoutgoing.ssh=python:vcsserver.hooks.pre_pull_ssh
54 outgoing.ssh=python:vcsserver.hooks.post_pull_ssh
49 # RhodeCode SSH hooks version=2.0.0
50 {custom}
51 '''
52 ).format(custom='\n'.join(hg_flags))
55 53
56 '''
57 )
54 root = self.server.get_root_store()
55 hgrc_custom = os.path.join(root, repo_name, '.hg', 'hgrc_rhodecode')
56 hgrc_main = os.path.join(root, repo_name, '.hg', 'hgrc')
58 57
58 # cleanup custom hgrc file
59 if os.path.isfile(hgrc_custom):
60 with open(hgrc_custom, 'wb') as f:
61 f.write('')
62 log.debug('Cleanup custom hgrc file under %s', hgrc_custom)
63
64 # write temp
59 65 with os.fdopen(self.hooks_env_fd, 'w') as hooks_env_file:
60 66 hooks_env_file.write(content)
61 root = self.server.get_root_store()
62 67
63 hgrc_custom = os.path.join(
64 root, self.server.repo_name, '.hg', 'hgrc_rhodecode')
65 log.debug('Wrote custom hgrc file under %s', hgrc_custom)
66 shutil.move(
67 self.hooks_env_path, hgrc_custom)
68
69 hgrc_main = os.path.join(
70 root, self.server.repo_name, '.hg', 'hgrc')
71 include_marker = '%include hgrc_rhodecode'
68 return self.hooks_env_path
72 69
73 if not os.path.isfile(hgrc_main):
74 os.mknod(hgrc_main)
75
76 with open(hgrc_main, 'rb') as f:
77 data = f.read()
78 has_marker = include_marker in data
70 def remove_configs(self):
71 os.remove(self.hooks_env_path)
79 72
80 if not has_marker:
81 log.debug('Adding include marker for hooks')
82 with open(hgrc_main, 'wa') as f:
83 f.write(textwrap.dedent('''
84 # added by RhodeCode
85 {}
86 '''.format(include_marker)))
87
88 def command(self):
73 def command(self, hgrc_path):
89 74 root = self.server.get_root_store()
90 75
91 76 command = (
92 "cd {root}; {hg_path} -R {root}{repo_name} "
77 "cd {root}; HGRCPATH={hgrc} {hg_path} -R {root}{repo_name} "
93 78 "serve --stdio".format(
94 79 root=root, hg_path=self.server.hg_path,
95 repo_name=self.server.repo_name))
80 repo_name=self.server.repo_name, hgrc=hgrc_path))
96 81 log.debug("Final CMD: %s", command)
97 82 return command
98 83
@@ -102,22 +87,61 b' class MercurialTunnelWrapper(object):'
102 87 action = '?'
103 88 # permissions are check via `pre_push_ssh_auth` hook
104 89 self.server.update_environment(action=action, extras=extras)
105 self.create_hooks_env()
106 return os.system(self.command())
90 custom_hgrc_file = self.create_hooks_env()
91
92 try:
93 return os.system(self.command(custom_hgrc_file))
94 finally:
95 self.remove_configs()
107 96
108 97
109 98 class MercurialServer(VcsServer):
110 99 backend = 'hg'
100 cli_flags = ['phases', 'largefiles', 'extensions', 'experimental', 'hooks']
111 101
112 def __init__(self, store, ini_path, repo_name,
113 user, user_permissions, config, env):
114 super(MercurialServer, self).\
115 __init__(user, user_permissions, config, env)
102 def __init__(self, store, ini_path, repo_name, user, user_permissions, config, env):
103 super(MercurialServer, self).__init__(user, user_permissions, config, env)
116 104
117 105 self.store = store
118 106 self.ini_path = ini_path
119 107 self.repo_name = repo_name
120 self._path = self.hg_path = config.get(
121 'app:main', 'ssh.executable.hg')
108 self._path = self.hg_path = config.get('app:main', 'ssh.executable.hg')
109 self.tunnel = MercurialTunnelWrapper(server=self)
110
111 def config_to_hgrc(self, repo_name):
112 ui_sections = collections.defaultdict(list)
113 ui = VcsSettingsModel(repo=repo_name).get_ui_settings(section=None, key=None)
114
115 # write default hooks
116 default_hooks = [
117 ('pretxnchangegroup.ssh_auth', 'python:vcsserver.hooks.pre_push_ssh_auth'),
118 ('pretxnchangegroup.ssh', 'python:vcsserver.hooks.pre_push_ssh'),
119 ('changegroup.ssh', 'python:vcsserver.hooks.post_push_ssh'),
120
121 ('preoutgoing.ssh', 'python:vcsserver.hooks.pre_pull_ssh'),
122 ('outgoing.ssh', 'python:vcsserver.hooks.post_pull_ssh'),
123 ]
124
125 for k, v in default_hooks:
126 ui_sections['hooks'].append((k, v))
122 127
123 self.tunnel = MercurialTunnelWrapper(server=self)
128 for entry in ui:
129 if not entry.active:
130 continue
131 sec = entry.section
132 key = entry.key
133
134 if sec in self.cli_flags:
135 # we want only custom hooks, so we skip builtins
136 if sec == 'hooks' and key in RhodeCodeUi.HOOKS_BUILTIN:
137 continue
138
139 ui_sections[sec].append([key, entry.value])
140
141 flags = []
142 for _sec, key_val in ui_sections.items():
143 flags.append(' ')
144 flags.append('[{}]'.format(_sec))
145 for key, val in key_val:
146 flags.append('{}= {}'.format(key, val))
147 return flags
@@ -18,6 +18,7 b''
18 18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20 20
21 import os
21 22 import mock
22 23 import pytest
23 24
@@ -68,14 +69,16 b' def hg_server(app):'
68 69
69 70 class TestMercurialServer(object):
70 71
71 def test_command(self, hg_server):
72 def test_command(self, hg_server, tmpdir):
72 73 server = hg_server.create()
74 custom_hgrc = os.path.join(str(tmpdir), 'hgrc')
73 75 expected_command = (
74 'cd {root}; {hg_path} -R {root}{repo_name} serve --stdio'.format(
75 root=hg_server.root, hg_path=hg_server.hg_path,
76 'cd {root}; HGRCPATH={custom_hgrc} {hg_path} -R {root}{repo_name} serve --stdio'.format(
77 root=hg_server.root, custom_hgrc=custom_hgrc, hg_path=hg_server.hg_path,
76 78 repo_name=hg_server.repo_name)
77 79 )
78 assert expected_command == server.tunnel.command()
80 server_command = server.tunnel.command(custom_hgrc)
81 assert expected_command == server_command
79 82
80 83 @pytest.mark.parametrize('permissions, action, code', [
81 84 ({}, 'pull', -2),
This diff has been collapsed as it changes many lines, (914 lines changed) Show them Hide them
@@ -28,23 +28,16 b''
28 28 {
29 29 "license": [
30 30 {
31 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
32 "shortName": "bsdOriginal",
33 "spdxId": "BSD-4-Clause",
34 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
35 }
36 ],
37 "name": "python2.7-coverage-3.7.1"
38 },
39 {
40 "license": [
41 {
42 31 "fullName": "MIT License",
43 32 "shortName": "mit",
44 33 "spdxId": "MIT",
45 34 "url": "http://spdx.org/licenses/MIT.html"
46 35 }
47 36 ],
37 "name": "python2.7-beautifulsoup4-4.6.3"
38 },
39 {
40 "license": "UNKNOWN",
48 41 "name": "python2.7-bootstrapped-pip-9.0.1"
49 42 },
50 43 {
@@ -56,29 +49,7 b''
56 49 "url": "http://spdx.org/licenses/MIT.html"
57 50 }
58 51 ],
59 "name": "python2.7-cov-core-1.15.0"
60 },
61 {
62 "license": [
63 {
64 "fullName": "MIT License",
65 "shortName": "mit",
66 "spdxId": "MIT",
67 "url": "http://spdx.org/licenses/MIT.html"
68 }
69 ],
70 "name": "python2.7-webtest-2.0.29"
71 },
72 {
73 "license": [
74 {
75 "fullName": "MIT License",
76 "shortName": "mit",
77 "spdxId": "MIT",
78 "url": "http://spdx.org/licenses/MIT.html"
79 }
80 ],
81 "name": "python2.7-beautifulsoup4-4.6.3"
52 "name": "python2.7-webtest-2.0.32"
82 53 },
83 54 {
84 55 "license": [
@@ -100,7 +71,7 b''
100 71 "url": "http://spdx.org/licenses/MIT.html"
101 72 }
102 73 ],
103 "name": "python2.7-webob-1.7.4"
74 "name": "python2.7-webob-1.8.4"
104 75 },
105 76 {
106 77 "license": [
@@ -116,6 +87,28 b''
116 87 {
117 88 "license": [
118 89 {
90 "fullName": "Apache License 2.0",
91 "shortName": "asl20",
92 "spdxId": "Apache-2.0",
93 "url": "http://spdx.org/licenses/Apache-2.0.html"
94 }
95 ],
96 "name": "python2.7-coverage-4.5.1"
97 },
98 {
99 "license": [
100 {
101 "fullName": "MIT License",
102 "shortName": "mit",
103 "spdxId": "MIT",
104 "url": "http://spdx.org/licenses/MIT.html"
105 }
106 ],
107 "name": "python2.7-cov-core-1.15.0"
108 },
109 {
110 "license": [
111 {
119 112 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
120 113 "shortName": "bsdOriginal",
121 114 "spdxId": "BSD-4-Clause",
@@ -127,6 +120,17 b''
127 120 {
128 121 "license": [
129 122 {
123 "fullName": "GNU Lesser General Public License v3 or later (LGPLv3+)"
124 },
125 {
126 "fullName": "LGPL"
127 }
128 ],
129 "name": "python2.7-gprof2dot-2017.9.19"
130 },
131 {
132 "license": [
133 {
130 134 "fullName": "MIT License",
131 135 "shortName": "mit",
132 136 "spdxId": "MIT",
@@ -136,7 +140,7 b''
136 140 "fullName": "DFSG approved"
137 141 }
138 142 ],
139 "name": "python2.7-pytest-timeout-1.2.1"
143 "name": "python2.7-pytest-timeout-1.3.2"
140 144 },
141 145 {
142 146 "license": [
@@ -147,7 +151,32 b''
147 151 "url": "http://spdx.org/licenses/MIT.html"
148 152 }
149 153 ],
150 "name": "python2.7-pytest-3.6.0"
154 "name": "python2.7-pytest-3.8.2"
155 },
156 {
157 "license": [
158 {
159 "fullName": "MIT License",
160 "shortName": "mit",
161 "spdxId": "MIT",
162 "url": "http://spdx.org/licenses/MIT.html"
163 }
164 ],
165 "name": "python2.7-pathlib2-2.3.3"
166 },
167 {
168 "license": [
169 {
170 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
171 "shortName": "bsdOriginal",
172 "spdxId": "BSD-4-Clause",
173 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
174 },
175 {
176 "fullName": "New BSD License"
177 }
178 ],
179 "name": "python2.7-scandir-1.9.0"
151 180 },
152 181 {
153 182 "license": [
@@ -172,7 +201,7 b''
172 201 "url": "http://spdx.org/licenses/MIT.html"
173 202 }
174 203 ],
175 "name": "python2.7-pluggy-0.6.0"
204 "name": "python2.7-pluggy-0.9.0"
176 205 },
177 206 {
178 207 "license": [
@@ -183,7 +212,7 b''
183 212 "url": "http://spdx.org/licenses/MIT.html"
184 213 }
185 214 ],
186 "name": "python2.7-atomicwrites-1.1.5"
215 "name": "python2.7-atomicwrites-1.2.1"
187 216 },
188 217 {
189 218 "license": [
@@ -194,7 +223,7 b''
194 223 "url": "http://spdx.org/licenses/MIT.html"
195 224 }
196 225 ],
197 "name": "python2.7-more-itertools-4.3.0"
226 "name": "python2.7-more-itertools-5.0.0"
198 227 },
199 228 {
200 229 "license": [
@@ -205,7 +234,7 b''
205 234 "url": "http://spdx.org/licenses/MIT.html"
206 235 }
207 236 ],
208 "name": "python2.7-attrs-18.1.0"
237 "name": "python2.7-attrs-18.2.0"
209 238 },
210 239 {
211 240 "license": [
@@ -216,18 +245,7 b''
216 245 "url": "http://spdx.org/licenses/MIT.html"
217 246 }
218 247 ],
219 "name": "python2.7-py-1.5.3"
220 },
221 {
222 "license": [
223 {
224 "fullName": "GNU Lesser General Public License v3 or later (LGPLv3+)"
225 },
226 {
227 "fullName": "LGPL"
228 }
229 ],
230 "name": "python2.7-gprof2dot-2017.9.19"
248 "name": "python2.7-py-1.6.0"
231 249 },
232 250 {
233 251 "license": [
@@ -254,17 +272,6 b''
254 272 {
255 273 "license": [
256 274 {
257 "fullName": "MIT License",
258 "shortName": "mit",
259 "spdxId": "MIT",
260 "url": "http://spdx.org/licenses/MIT.html"
261 }
262 ],
263 "name": "python2.7-setuptools-scm-2.1.0"
264 },
265 {
266 "license": [
267 {
268 275 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
269 276 "shortName": "bsdOriginal",
270 277 "spdxId": "BSD-4-Clause",
@@ -299,7 +306,7 b''
299 306 "url": "http://spdx.org/licenses/MIT.html"
300 307 }
301 308 ],
302 "name": "python2.7-pytest-cov-2.5.1"
309 "name": "python2.7-pytest-cov-2.6.0"
303 310 },
304 311 {
305 312 "license": [
@@ -310,7 +317,7 b''
310 317 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
311 318 }
312 319 ],
313 "name": "python2.7-appenlight-client-0.6.25"
320 "name": "python2.7-appenlight-client-0.6.26"
314 321 },
315 322 {
316 323 "license": [
@@ -326,10 +333,107 b''
326 333 {
327 334 "license": [
328 335 {
329 "fullName": "AGPLv3 and Proprietary"
336 "fullName": "Apache 2.0 and Proprietary"
337 }
338 ],
339 "name": "python2.7-rhodecode-tools-1.2.1"
340 },
341 {
342 "license": [
343 {
344 "fullName": "Apache License 2.0",
345 "shortName": "asl20",
346 "spdxId": "Apache-2.0",
347 "url": "http://spdx.org/licenses/Apache-2.0.html"
348 }
349 ],
350 "name": "python2.7-elasticsearch1-dsl-0.0.12"
351 },
352 {
353 "license": [
354 {
355 "fullName": "Apache License 2.0",
356 "shortName": "asl20",
357 "spdxId": "Apache-2.0",
358 "url": "http://spdx.org/licenses/Apache-2.0.html"
359 }
360 ],
361 "name": "python2.7-elasticsearch1-1.10.0"
362 },
363 {
364 "license": [
365 {
366 "fullName": "MIT License",
367 "shortName": "mit",
368 "spdxId": "MIT",
369 "url": "http://spdx.org/licenses/MIT.html"
330 370 }
331 371 ],
332 "name": "python2.7-rhodecode-tools-0.16.0"
372 "name": "python2.7-urllib3-1.24.1"
373 },
374 {
375 "license": [
376 {
377 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
378 "shortName": "bsdOriginal",
379 "spdxId": "BSD-4-Clause",
380 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
381 },
382 {
383 "fullName": "Apache License 2.0",
384 "shortName": "asl20",
385 "spdxId": "Apache-2.0",
386 "url": "http://spdx.org/licenses/Apache-2.0.html"
387 },
388 {
389 "fullName": "Dual License"
390 }
391 ],
392 "name": "python2.7-python-dateutil-2.8.0"
393 },
394 {
395 "license": [
396 {
397 "fullName": "Apache License 2.0",
398 "shortName": "asl20",
399 "spdxId": "Apache-2.0",
400 "url": "http://spdx.org/licenses/Apache-2.0.html"
401 }
402 ],
403 "name": "python2.7-elasticsearch2-2.5.0"
404 },
405 {
406 "license": [
407 {
408 "fullName": "Apache License 2.0",
409 "shortName": "asl20",
410 "spdxId": "Apache-2.0",
411 "url": "http://spdx.org/licenses/Apache-2.0.html"
412 }
413 ],
414 "name": "python2.7-elasticsearch-dsl-6.3.1"
415 },
416 {
417 "license": [
418 {
419 "fullName": "Python Software Foundation License version 2",
420 "shortName": "psfl",
421 "spdxId": "Python-2.0",
422 "url": "http://spdx.org/licenses/Python-2.0.html"
423 }
424 ],
425 "name": "python2.7-ipaddress-1.0.22"
426 },
427 {
428 "license": [
429 {
430 "fullName": "Apache License 2.0",
431 "shortName": "asl20",
432 "spdxId": "Apache-2.0",
433 "url": "http://spdx.org/licenses/Apache-2.0.html"
434 }
435 ],
436 "name": "python2.7-elasticsearch-6.3.1"
333 437 },
334 438 {
335 439 "license": [
@@ -351,66 +455,13 b''
351 455 {
352 456 "license": [
353 457 {
354 "fullName": "MIT License",
355 "shortName": "mit",
356 "spdxId": "MIT",
357 "url": "http://spdx.org/licenses/MIT.html"
358 }
359 ],
360 "name": "python2.7-urllib3-1.21"
361 },
362 {
363 "license": [
364 {
365 "fullName": "Apache License 2.0",
366 "shortName": "asl20",
367 "spdxId": "Apache-2.0",
368 "url": "http://spdx.org/licenses/Apache-2.0.html"
369 }
370 ],
371 "name": "python2.7-elasticsearch-dsl-2.2.0"
372 },
373 {
374 "license": [
375 {
376 "fullName": "Apache License 2.0",
377 "shortName": "asl20",
378 "spdxId": "Apache-2.0",
379 "url": "http://spdx.org/licenses/Apache-2.0.html"
380 }
381 ],
382 "name": "python2.7-elasticsearch-2.3.0"
383 },
384 {
385 "license": [
386 {
387 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
388 "shortName": "bsdOriginal",
389 "spdxId": "BSD-4-Clause",
390 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
391 },
392 {
393 "fullName": "Apache License 2.0",
394 "shortName": "asl20",
395 "spdxId": "Apache-2.0",
396 "url": "http://spdx.org/licenses/Apache-2.0.html"
397 },
398 {
399 "fullName": "Dual License"
400 }
401 ],
402 "name": "python2.7-python-dateutil-2.7.3"
403 },
404 {
405 "license": [
406 {
407 458 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
408 459 "shortName": "bsdOriginal",
409 460 "spdxId": "BSD-4-Clause",
410 461 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
411 462 }
412 463 ],
413 "name": "python2.7-markupsafe-1.0"
464 "name": "python2.7-markupsafe-1.1.0"
414 465 },
415 466 {
416 467 "license": [
@@ -443,29 +494,7 b''
443 494 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
444 495 }
445 496 ],
446 "name": "python2.7-click-6.6"
447 },
448 {
449 "license": [
450 {
451 "fullName": "MIT License",
452 "shortName": "mit",
453 "spdxId": "MIT",
454 "url": "http://spdx.org/licenses/MIT.html"
455 }
456 ],
457 "name": "python2.7-bottle-0.12.13"
458 },
459 {
460 "license": [
461 {
462 "fullName": "MIT License",
463 "shortName": "mit",
464 "spdxId": "MIT",
465 "url": "http://spdx.org/licenses/MIT.html"
466 }
467 ],
468 "name": "python2.7-cprofilev-1.0.7"
497 "name": "python2.7-click-7.0"
469 498 },
470 499 {
471 500 "license": [
@@ -519,31 +548,6 b''
519 548 "url": "http://spdx.org/licenses/MIT.html"
520 549 }
521 550 ],
522 "name": "python2.7-pathlib2-2.3.0"
523 },
524 {
525 "license": [
526 {
527 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
528 "shortName": "bsdOriginal",
529 "spdxId": "BSD-4-Clause",
530 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
531 },
532 {
533 "fullName": "New BSD License"
534 }
535 ],
536 "name": "python2.7-scandir-1.9.0"
537 },
538 {
539 "license": [
540 {
541 "fullName": "MIT License",
542 "shortName": "mit",
543 "spdxId": "MIT",
544 "url": "http://spdx.org/licenses/MIT.html"
545 }
546 ],
547 551 "name": "python2.7-backports.shutil-get-terminal-size-1.0.0"
548 552 },
549 553 {
@@ -555,7 +559,7 b''
555 559 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
556 560 }
557 561 ],
558 "name": "python2.7-pygments-2.2.0"
562 "name": "python2.7-pygments-2.3.1"
559 563 },
560 564 {
561 565 "license": [
@@ -646,7 +650,7 b''
646 650 "url": "http://spdx.org/licenses/MIT.html"
647 651 }
648 652 ],
649 "name": "python2.7-pickleshare-0.7.4"
653 "name": "python2.7-pickleshare-0.7.5"
650 654 },
651 655 {
652 656 "license": [
@@ -690,7 +694,7 b''
690 694 "url": "http://spdx.org/licenses/MIT.html"
691 695 }
692 696 ],
693 "name": "python2.7-greenlet-0.4.13"
697 "name": "python2.7-greenlet-0.4.15"
694 698 },
695 699 {
696 700 "license": [
@@ -701,7 +705,7 b''
701 705 "url": "http://spdx.org/licenses/MIT.html"
702 706 }
703 707 ],
704 "name": "python2.7-gevent-1.3.5"
708 "name": "python2.7-gevent-1.4.0"
705 709 },
706 710 {
707 711 "license": [
@@ -712,7 +716,7 b''
712 716 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
713 717 }
714 718 ],
715 "name": "python2.7-psutil-5.4.6"
719 "name": "python2.7-psutil-5.5.1"
716 720 },
717 721 {
718 722 "license": [
@@ -745,7 +749,7 b''
745 749 "url": "http://spdx.org/licenses/MIT.html"
746 750 }
747 751 ],
748 "name": "python2.7-alembic-0.9.9"
752 "name": "python2.7-alembic-1.0.5"
749 753 },
750 754 {
751 755 "license": {
@@ -754,7 +758,7 b''
754 758 "spdxId": "Apache-2.0",
755 759 "url": "http://spdx.org/licenses/Apache-2.0.html"
756 760 },
757 "name": "python2.7-python-editor-1.0.3"
761 "name": "python2.7-python-editor-1.0.4"
758 762 },
759 763 {
760 764 "license": [
@@ -842,39 +846,6 b''
842 846 {
843 847 "license": [
844 848 {
845 "fullName": "Apache License 2.0",
846 "shortName": "asl20",
847 "spdxId": "Apache-2.0",
848 "url": "http://spdx.org/licenses/Apache-2.0.html"
849 }
850 ],
851 "name": "python2.7-bleach-2.1.4"
852 },
853 {
854 "license": [
855 {
856 "fullName": "MIT License",
857 "shortName": "mit",
858 "spdxId": "MIT",
859 "url": "http://spdx.org/licenses/MIT.html"
860 }
861 ],
862 "name": "python2.7-html5lib-1.0.1"
863 },
864 {
865 "license": [
866 {
867 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
868 "shortName": "bsdOriginal",
869 "spdxId": "BSD-4-Clause",
870 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
871 }
872 ],
873 "name": "python2.7-webencodings-0.5.1"
874 },
875 {
876 "license": [
877 {
878 849 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
879 850 "shortName": "bsdOriginal",
880 851 "spdxId": "BSD-4-Clause",
@@ -892,7 +863,7 b''
892 863 "url": "http://spdx.org/licenses/MIT.html"
893 864 }
894 865 ],
895 "name": "python2.7-testpath-0.3.1"
866 "name": "python2.7-testpath-0.4.2"
896 867 },
897 868 {
898 869 "license": [
@@ -908,6 +879,28 b''
908 879 {
909 880 "license": [
910 881 {
882 "fullName": "Apache License 2.0",
883 "shortName": "asl20",
884 "spdxId": "Apache-2.0",
885 "url": "http://spdx.org/licenses/Apache-2.0.html"
886 }
887 ],
888 "name": "python2.7-bleach-3.1.0"
889 },
890 {
891 "license": [
892 {
893 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
894 "shortName": "bsdOriginal",
895 "spdxId": "BSD-4-Clause",
896 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
897 }
898 ],
899 "name": "python2.7-webencodings-0.5.1"
900 },
901 {
902 "license": [
903 {
911 904 "fullName": "MIT License",
912 905 "shortName": "mit",
913 906 "spdxId": "MIT",
@@ -925,7 +918,7 b''
925 918 "url": "http://spdx.org/licenses/MIT.html"
926 919 }
927 920 ],
928 "name": "python2.7-configparser-3.5.0"
921 "name": "python2.7-configparser-3.7.3"
929 922 },
930 923 {
931 924 "license": [
@@ -947,7 +940,73 b''
947 940 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
948 941 }
949 942 ],
950 "name": "python2.7-mistune-0.8.3"
943 "name": "python2.7-mistune-0.8.4"
944 },
945 {
946 "license": {
947 "fullName": "GNU Lesser General Public License v3.0 or later",
948 "shortName": "lgpl3Plus",
949 "spdxId": "LGPL-3.0+",
950 "url": "http://spdx.org/licenses/LGPL-3.0+.html"
951 },
952 "name": "python2.7-psycopg2-2.7.7"
953 },
954 {
955 "license": {
956 "fullName": "PostgreSQL License",
957 "shortName": "postgresql",
958 "spdxId": "PostgreSQL",
959 "url": "http://spdx.org/licenses/PostgreSQL.html"
960 },
961 "name": "postgresql-9.6.10"
962 },
963 {
964 "license": [
965 {
966 "fullName": "zlib License",
967 "shortName": "zlib",
968 "spdxId": "Zlib",
969 "url": "http://spdx.org/licenses/Zlib.html"
970 },
971 {
972 "fullName": "libpng License",
973 "shortName": "libpng",
974 "spdxId": "Libpng",
975 "url": "http://spdx.org/licenses/Libpng.html"
976 }
977 ],
978 "name": "python2.7-pysqlite-2.8.3"
979 },
980 {
981 "license": [
982 {
983 "fullName": "MIT License",
984 "shortName": "mit",
985 "spdxId": "MIT",
986 "url": "http://spdx.org/licenses/MIT.html"
987 }
988 ],
989 "name": "python2.7-pymysql-0.8.1"
990 },
991 {
992 "license": [
993 {
994 "fullName": "GNU General Public License v1.0 only",
995 "shortName": "gpl1",
996 "spdxId": "GPL-1.0",
997 "url": "http://spdx.org/licenses/GPL-1.0.html"
998 }
999 ],
1000 "name": "python2.7-mysql-python-1.2.5"
1001 },
1002 {
1003 "license": {
1004 "fullName": "GNU Library General Public License v2.1 only",
1005 "shortName": "lgpl21",
1006 "spdxId": "LGPL-2.1",
1007 "url": "http://spdx.org/licenses/LGPL-2.1.html"
1008 },
1009 "name": "mariadb-connector-c-2.3.4"
951 1010 },
952 1011 {
953 1012 "license": [
@@ -958,7 +1017,7 b''
958 1017 "url": "http://spdx.org/licenses/ZPL-2.1.html"
959 1018 }
960 1019 ],
961 "name": "python2.7-zope.interface-4.5.0"
1020 "name": "python2.7-zope.interface-4.6.0"
962 1021 },
963 1022 {
964 1023 "license": [
@@ -969,7 +1028,7 b''
969 1028 "url": "http://spdx.org/licenses/ZPL-2.1.html"
970 1029 }
971 1030 ],
972 "name": "python2.7-zope.event-4.3.0"
1031 "name": "python2.7-zope.event-4.4"
973 1032 },
974 1033 {
975 1034 "license": [
@@ -980,7 +1039,7 b''
980 1039 "url": "http://spdx.org/licenses/ZPL-2.1.html"
981 1040 }
982 1041 ],
983 "name": "python2.7-zope.deprecation-4.3.0"
1042 "name": "python2.7-zope.deprecation-4.4.0"
984 1043 },
985 1044 {
986 1045 "license": [
@@ -1043,7 +1102,7 b''
1043 1102 "url": "http://spdx.org/licenses/MIT.html"
1044 1103 }
1045 1104 ],
1046 "name": "python2.7-paste-2.0.3"
1105 "name": "python2.7-paste-3.0.5"
1047 1106 },
1048 1107 {
1049 1108 "license": [
@@ -1061,7 +1120,7 b''
1061 1120 "fullName": "Repoze License",
1062 1121 "url": "http://www.repoze.org/LICENSE.txt"
1063 1122 },
1064 "name": "python2.7-venusian-1.1.0"
1123 "name": "python2.7-venusian-1.2.0"
1065 1124 },
1066 1125 {
1067 1126 "license": {
@@ -1072,17 +1131,6 b''
1072 1131 "name": "python2.7-urlobject-2.4.3"
1073 1132 },
1074 1133 {
1075 "license": [
1076 {
1077 "fullName": "Apache License 2.0",
1078 "shortName": "asl20",
1079 "spdxId": "Apache-2.0",
1080 "url": "http://spdx.org/licenses/Apache-2.0.html"
1081 }
1082 ],
1083 "name": "python2.7-trollius-1.0.4"
1084 },
1085 {
1086 1134 "license": {
1087 1135 "fullName": "Repoze License",
1088 1136 "url": "http://www.repoze.org/LICENSE.txt"
@@ -1095,7 +1143,7 b''
1095 1143 "fullName": "BSD-derived (http://www.repoze.org/LICENSE.txt)"
1096 1144 }
1097 1145 ],
1098 "name": "python2.7-supervisor-3.3.4"
1146 "name": "python2.7-supervisor-3.3.5"
1099 1147 },
1100 1148 {
1101 1149 "license": [
@@ -1114,7 +1162,7 b''
1114 1162 "url": "http://spdx.org/licenses/Python-2.0.html"
1115 1163 }
1116 1164 ],
1117 "name": "python2.7-subprocess32-3.5.1"
1165 "name": "python2.7-subprocess32-3.5.3"
1118 1166 },
1119 1167 {
1120 1168 "license": [
@@ -1125,7 +1173,7 b''
1125 1173 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1126 1174 }
1127 1175 ],
1128 "name": "python2.7-sshpubkeys-2.2.0"
1176 "name": "python2.7-sshpubkeys-3.1.0"
1129 1177 },
1130 1178 {
1131 1179 "license": [
@@ -1141,11 +1189,55 b''
1141 1189 {
1142 1190 "license": [
1143 1191 {
1144 "fullName": "Public Domain",
1145 "shortName": "publicDomain"
1192 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1193 "shortName": "bsdOriginal",
1194 "spdxId": "BSD-4-Clause",
1195 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1196 },
1197 {
1198 "fullName": "BSD or Apache License, Version 2.0"
1199 },
1200 {
1201 "fullName": "Apache License 2.0",
1202 "shortName": "asl20",
1203 "spdxId": "Apache-2.0",
1204 "url": "http://spdx.org/licenses/Apache-2.0.html"
1146 1205 }
1147 1206 ],
1148 "name": "python2.7-pycrypto-2.6.1"
1207 "name": "python2.7-cryptography-2.5"
1208 },
1209 {
1210 "license": [
1211 {
1212 "fullName": "MIT License",
1213 "shortName": "mit",
1214 "spdxId": "MIT",
1215 "url": "http://spdx.org/licenses/MIT.html"
1216 }
1217 ],
1218 "name": "python2.7-cffi-1.12.1"
1219 },
1220 {
1221 "license": [
1222 {
1223 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1224 "shortName": "bsdOriginal",
1225 "spdxId": "BSD-4-Clause",
1226 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1227 }
1228 ],
1229 "name": "python2.7-pycparser-2.19"
1230 },
1231 {
1232 "license": [
1233 {
1234 "fullName": "MIT License",
1235 "shortName": "mit",
1236 "spdxId": "MIT",
1237 "url": "http://spdx.org/licenses/MIT.html"
1238 }
1239 ],
1240 "name": "python2.7-asn1crypto-0.24.0"
1149 1241 },
1150 1242 {
1151 1243 "license": [
@@ -1159,18 +1251,7 b''
1159 1251 "url": "http://spdx.org/licenses/MIT.html"
1160 1252 }
1161 1253 ],
1162 "name": "python2.7-simplejson-3.11.1"
1163 },
1164 {
1165 "license": [
1166 {
1167 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1168 "shortName": "bsdOriginal",
1169 "spdxId": "BSD-4-Clause",
1170 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1171 }
1172 ],
1173 "name": "python2.7-setproctitle-1.1.10"
1254 "name": "python2.7-simplejson-3.16.0"
1174 1255 },
1175 1256 {
1176 1257 "license": [
@@ -1210,7 +1291,7 b''
1210 1291 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1211 1292 }
1212 1293 ],
1213 "name": "python2.7-py-gfm-0.1.3"
1294 "name": "python2.7-py-gfm-0.1.4"
1214 1295 },
1215 1296 {
1216 1297 "license": [
@@ -1248,6 +1329,72 b''
1248 1329 {
1249 1330 "license": [
1250 1331 {
1332 "fullName": "MIT License",
1333 "shortName": "mit",
1334 "spdxId": "MIT",
1335 "url": "http://spdx.org/licenses/MIT.html"
1336 }
1337 ],
1338 "name": "python2.7-python-saml-2.4.2"
1339 },
1340 {
1341 "license": [
1342 {
1343 "fullName": "Python Software Foundation License version 2",
1344 "shortName": "psfl",
1345 "spdxId": "Python-2.0",
1346 "url": "http://spdx.org/licenses/Python-2.0.html"
1347 }
1348 ],
1349 "name": "python2.7-defusedxml-0.5.0"
1350 },
1351 {
1352 "license": [
1353 {
1354 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1355 "shortName": "bsdOriginal",
1356 "spdxId": "BSD-4-Clause",
1357 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1358 }
1359 ],
1360 "name": "python2.7-isodate-0.6.0"
1361 },
1362 {
1363 "license": [
1364 {
1365 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1366 "shortName": "bsdOriginal",
1367 "spdxId": "BSD-4-Clause",
1368 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1369 }
1370 ],
1371 "name": "python2.7-dm.xmlsec.binding-1.3.7"
1372 },
1373 {
1374 "license": [
1375 {
1376 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1377 "shortName": "bsdOriginal",
1378 "spdxId": "BSD-4-Clause",
1379 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1380 }
1381 ],
1382 "name": "python2.7-lxml-4.2.5"
1383 },
1384 {
1385 "license": [
1386 {
1387 "fullName": "MIT License",
1388 "shortName": "mit",
1389 "spdxId": "MIT",
1390 "url": "http://spdx.org/licenses/MIT.html"
1391 }
1392 ],
1393 "name": "python2.7-wheel-0.30.0"
1394 },
1395 {
1396 "license": [
1397 {
1251 1398 "fullName": "License :: OSI Approved :: MIT License"
1252 1399 },
1253 1400 {
@@ -1260,14 +1407,7 b''
1260 1407 "name": "python2.7-python-pam-1.8.4"
1261 1408 },
1262 1409 {
1263 "license": [
1264 {
1265 "fullName": "GNU General Public License v1.0 only",
1266 "shortName": "gpl1",
1267 "spdxId": "GPL-1.0",
1268 "url": "http://spdx.org/licenses/GPL-1.0.html"
1269 }
1270 ],
1410 "license": "UNKNOWN",
1271 1411 "name": "linux-pam-1.3.0"
1272 1412 },
1273 1413 {
@@ -1302,9 +1442,7 b''
1302 1442 "name": "libkrb5-1.15.2"
1303 1443 },
1304 1444 {
1305 "license":{
1306 "fullName": "BSD-derived (https://www.openldap.org/software/release/license.html)"
1307 },
1445 "license": "UNKNOWN",
1308 1446 "name": "openldap-2.4.45"
1309 1447 },
1310 1448 {
@@ -1316,7 +1454,18 b''
1316 1454 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1317 1455 }
1318 1456 ],
1319 "name": "python2.7-pyasn1-modules-0.2.2"
1457 "name": "python2.7-pyasn1-modules-0.2.4"
1458 },
1459 {
1460 "license": [
1461 {
1462 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1463 "shortName": "bsdOriginal",
1464 "spdxId": "BSD-4-Clause",
1465 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1466 }
1467 ],
1468 "name": "python2.7-pyasn1-0.4.5"
1320 1469 },
1321 1470 {
1322 1471 "license": [
@@ -1327,42 +1476,36 b''
1327 1476 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1328 1477 }
1329 1478 ],
1330 "name": "python2.7-pyasn1-0.4.4"
1479 "name": "python2.7-pyramid-mailer-0.15.1"
1331 1480 },
1332 1481 {
1333 1482 "license": [
1334 1483 {
1335 "fullName": "zlib License",
1336 "shortName": "zlib",
1337 "spdxId": "Zlib",
1338 "url": "http://spdx.org/licenses/Zlib.html"
1339 },
1340 {
1341 "fullName": "libpng License",
1342 "shortName": "libpng",
1343 "spdxId": "Libpng",
1344 "url": "http://spdx.org/licenses/Libpng.html"
1484 "fullName": "Zope Public License 2.1",
1485 "shortName": "zpl21",
1486 "spdxId": "ZPL-2.1",
1487 "url": "http://spdx.org/licenses/ZPL-2.1.html"
1345 1488 }
1346 1489 ],
1347 "name": "python2.7-pysqlite-2.8.3"
1490 "name": "python2.7-transaction-2.4.0"
1491 },
1492 {
1493 "license": [
1494 {
1495 "fullName": "Zope Public License 2.1",
1496 "shortName": "zpl21",
1497 "spdxId": "ZPL-2.1",
1498 "url": "http://spdx.org/licenses/ZPL-2.1.html"
1499 }
1500 ],
1501 "name": "python2.7-repoze.sendmail-4.4.1"
1348 1502 },
1349 1503 {
1350 1504 "license": {
1351 1505 "fullName": "Repoze License",
1352 1506 "url": "http://www.repoze.org/LICENSE.txt"
1353 1507 },
1354 "name": "python2.7-pyramid-1.9.2"
1355 },
1356 {
1357 "license": [
1358 {
1359 "fullName": "MIT License",
1360 "shortName": "mit",
1361 "spdxId": "MIT",
1362 "url": "http://spdx.org/licenses/MIT.html"
1363 }
1364 ],
1365 "name": "python2.7-hupper-1.3"
1508 "name": "python2.7-pyramid-1.10.1"
1366 1509 },
1367 1510 {
1368 1511 "license": [
@@ -1395,7 +1538,18 b''
1395 1538 "url": "http://spdx.org/licenses/MIT.html"
1396 1539 }
1397 1540 ],
1398 "name": "python2.7-pastedeploy-1.5.2"
1541 "name": "python2.7-pastedeploy-2.0.1"
1542 },
1543 {
1544 "license": [
1545 {
1546 "fullName": "MIT License",
1547 "shortName": "mit",
1548 "spdxId": "MIT",
1549 "url": "http://spdx.org/licenses/MIT.html"
1550 }
1551 ],
1552 "name": "python2.7-hupper-1.5"
1399 1553 },
1400 1554 {
1401 1555 "license": {
@@ -1428,18 +1582,7 b''
1428 1582 "url": "http://www.repoze.org/LICENSE.txt"
1429 1583 }
1430 1584 ],
1431 "name": "python2.7-pyramid-debugtoolbar-4.4"
1432 },
1433 {
1434 "license": [
1435 {
1436 "fullName": "Python Software Foundation License version 2",
1437 "shortName": "psfl",
1438 "spdxId": "Python-2.0",
1439 "url": "http://spdx.org/licenses/Python-2.0.html"
1440 }
1441 ],
1442 "name": "python2.7-ipaddress-1.0.22"
1585 "name": "python2.7-pyramid-debugtoolbar-4.5"
1443 1586 },
1444 1587 {
1445 1588 "license": {
@@ -1468,29 +1611,16 b''
1468 1611 "url": "http://spdx.org/licenses/MIT.html"
1469 1612 }
1470 1613 ],
1471 "name": "python2.7-pyparsing-1.5.7"
1614 "name": "python2.7-pyparsing-2.3.0"
1472 1615 },
1473 1616 {
1474 1617 "license": [
1475 1618 {
1476 "fullName": "Apache License 2.0",
1477 "shortName": "asl20",
1478 "spdxId": "Apache-2.0",
1479 "url": "http://spdx.org/licenses/Apache-2.0.html"
1619 "fullName": "Public Domain",
1620 "shortName": "publicDomain"
1480 1621 }
1481 1622 ],
1482 "name": "python2.7-pygments-markdown-lexer-0.1.0.dev39"
1483 },
1484 {
1485 "license": [
1486 {
1487 "fullName": "MIT License",
1488 "shortName": "mit",
1489 "spdxId": "MIT",
1490 "url": "http://spdx.org/licenses/MIT.html"
1491 }
1492 ],
1493 "name": "python2.7-pyflakes-0.8.1"
1623 "name": "python2.7-pycrypto-2.6.1"
1494 1624 },
1495 1625 {
1496 1626 "license": {
@@ -1513,30 +1643,12 b''
1513 1643 "name": "python2.7-py-bcrypt-0.4"
1514 1644 },
1515 1645 {
1516 "license": {
1517 "fullName": "GNU Lesser General Public License v3.0 or later",
1518 "shortName": "lgpl3Plus",
1519 "spdxId": "LGPL-3.0+",
1520 "url": "http://spdx.org/licenses/LGPL-3.0+.html"
1521 },
1522 "name": "python2.7-psycopg2-2.7.4"
1523 },
1524 {
1525 "license": {
1526 "fullName": "PostgreSQL License",
1527 "shortName": "postgresql",
1528 "spdxId": "PostgreSQL",
1529 "url": "http://spdx.org/licenses/PostgreSQL.html"
1530 },
1531 "name": "postgresql-9.6.10"
1532 },
1533 {
1534 1646 "license": [
1535 1647 {
1536 1648 "fullName": "BSD-derived (http://www.repoze.org/LICENSE.txt)"
1537 1649 }
1538 1650 ],
1539 "name": "python2.7-peppercorn-0.5"
1651 "name": "python2.7-peppercorn-0.6"
1540 1652 },
1541 1653 {
1542 1654 "license": [
@@ -1547,7 +1659,7 b''
1547 1659 "url": "http://spdx.org/licenses/MIT.html"
1548 1660 }
1549 1661 ],
1550 "name": "python2.7-pastescript-2.0.2"
1662 "name": "python2.7-pastescript-3.0.0"
1551 1663 },
1552 1664 {
1553 1665 "license": [
@@ -1569,60 +1681,7 b''
1569 1681 "url": "http://spdx.org/licenses/MIT.html"
1570 1682 }
1571 1683 ],
1572 "name": "python2.7-objgraph-3.1.1"
1573 },
1574 {
1575 "license": [
1576 {
1577 "fullName": "MIT License",
1578 "shortName": "mit",
1579 "spdxId": "MIT",
1580 "url": "http://spdx.org/licenses/MIT.html"
1581 }
1582 ],
1583 "name": "python2.7-graphviz-0.9"
1584 },
1585 {
1586 "license": [
1587 {
1588 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1589 "shortName": "bsdOriginal",
1590 "spdxId": "BSD-4-Clause",
1591 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1592 }
1593 ],
1594 "name": "python2.7-pyotp-2.2.6"
1595 },
1596 {
1597 "license": [
1598 {
1599 "fullName": "MIT License",
1600 "shortName": "mit",
1601 "spdxId": "MIT",
1602 "url": "http://spdx.org/licenses/MIT.html"
1603 }
1604 ],
1605 "name": "python2.7-pymysql-0.8.1"
1606 },
1607 {
1608 "license": [
1609 {
1610 "fullName": "GNU General Public License v1.0 only",
1611 "shortName": "gpl1",
1612 "spdxId": "GPL-1.0",
1613 "url": "http://spdx.org/licenses/GPL-1.0.html"
1614 }
1615 ],
1616 "name": "python2.7-mysql-python-1.2.5"
1617 },
1618 {
1619 "license": {
1620 "fullName": "GNU Library General Public License v2.1 only",
1621 "shortName": "lgpl21",
1622 "spdxId": "LGPL-2.1",
1623 "url": "http://spdx.org/licenses/LGPL-2.1.html"
1624 },
1625 "name": "mariadb-connector-c-2.3.4"
1684 "name": "python2.7-pyotp-2.2.7"
1626 1685 },
1627 1686 {
1628 1687 "license": [
@@ -1644,29 +1703,7 b''
1644 1703 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1645 1704 }
1646 1705 ],
1647 "name": "python2.7-lxml-3.7.3"
1648 },
1649 {
1650 "license": [
1651 {
1652 "fullName": "MIT License",
1653 "shortName": "mit",
1654 "spdxId": "MIT",
1655 "url": "http://spdx.org/licenses/MIT.html"
1656 }
1657 ],
1658 "name": "python2.7-wheel-0.30.0"
1659 },
1660 {
1661 "license": [
1662 {
1663 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1664 "shortName": "bsdOriginal",
1665 "spdxId": "BSD-4-Clause",
1666 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1667 }
1668 ],
1669 "name": "python2.7-kombu-4.2.0"
1706 "name": "python2.7-kombu-4.2.1"
1670 1707 },
1671 1708 {
1672 1709 "license": [
@@ -1688,18 +1725,7 b''
1688 1725 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1689 1726 }
1690 1727 ],
1691 "name": "python2.7-vine-1.1.4"
1692 },
1693 {
1694 "license": [
1695 {
1696 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1697 "shortName": "bsdOriginal",
1698 "spdxId": "BSD-4-Clause",
1699 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1700 }
1701 ],
1702 "name": "python2.7-billiard-3.5.0.3"
1728 "name": "python2.7-vine-1.2.0"
1703 1729 },
1704 1730 {
1705 1731 "license": [
@@ -1721,7 +1747,7 b''
1721 1747 "url": "http://spdx.org/licenses/MIT.html"
1722 1748 }
1723 1749 ],
1724 "name": "python2.7-iso8601-0.1.11"
1750 "name": "python2.7-iso8601-0.1.12"
1725 1751 },
1726 1752 {
1727 1753 "license": [
@@ -1765,7 +1791,7 b''
1765 1791 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1766 1792 }
1767 1793 ],
1768 "name": "python2.7-dogpile.cache-0.6.6"
1794 "name": "python2.7-dogpile.cache-0.7.1"
1769 1795 },
1770 1796 {
1771 1797 "license": {
@@ -1779,17 +1805,20 b''
1779 1805 {
1780 1806 "license": [
1781 1807 {
1808 "fullName": "Repoze Public License"
1809 },
1810 {
1782 1811 "fullName": "BSD-derived (http://www.repoze.org/LICENSE.txt)"
1783 1812 }
1784 1813 ],
1785 "name": "python2.7-deform-2.0.5"
1814 "name": "python2.7-deform-2.0.7"
1786 1815 },
1787 1816 {
1788 1817 "license": {
1789 1818 "fullName": "Repoze License",
1790 1819 "url": "http://www.repoze.org/LICENSE.txt"
1791 1820 },
1792 "name": "python2.7-colander-1.4"
1821 "name": "python2.7-colander-1.7.0"
1793 1822 },
1794 1823 {
1795 1824 "license": [
@@ -1863,6 +1892,17 b''
1863 1892 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1864 1893 }
1865 1894 ],
1895 "name": "python2.7-billiard-3.5.0.3"
1896 },
1897 {
1898 "license": [
1899 {
1900 "fullName": "BSD 4-clause \"Original\" or \"Old\" License",
1901 "shortName": "bsdOriginal",
1902 "spdxId": "BSD-4-Clause",
1903 "url": "http://spdx.org/licenses/BSD-4-Clause.html"
1904 }
1905 ],
1866 1906 "name": "python2.7-babel-1.3"
1867 1907 },
1868 1908 {
@@ -1877,25 +1917,7 b''
1877 1917 "name": "python2.7-authomatic-0.1.0.post1"
1878 1918 },
1879 1919 {
1880 "license": [
1881 {
1882 "fullName": "MIT License",
1883 "shortName": "mit",
1884 "spdxId": "MIT",
1885 "url": "http://spdx.org/licenses/MIT.html"
1886 }
1887 ],
1888 "name": "node-grunt-cli-1.2.0"
1889 },
1890 {
1891 "license": [
1892 {
1893 "fullName": "MIT License",
1894 "shortName": "mit",
1895 "spdxId": "MIT",
1896 "url": "http://spdx.org/licenses/MIT.html"
1897 }
1898 ],
1920 "license": "UNKNOWN",
1899 1921 "name": "python2.7-rhodecode-testdata-0.10.0"
1900 1922 }
1901 1923 ]
@@ -250,7 +250,7 b' def includeme(config):'
250 250
251 251 # Includes which are required. The application would fail without them.
252 252 config.include('pyramid_mako')
253 config.include('pyramid_beaker')
253 config.include('rhodecode.lib.rc_beaker')
254 254 config.include('rhodecode.lib.rc_cache')
255 255
256 256 config.include('rhodecode.apps._base.navigation')
@@ -28,8 +28,8 b' def _pre_push_hook(*args, **kwargs):'
28 28 [{u'hg_env|git_env': ...,
29 29 u'multiple_heads': [],
30 30 u'name': u'default',
31 u'new_rev': u'd0befe0692e722e01d5677f27a104631cf798b69',
32 u'old_rev': u'd0befe0692e722e01d5677f27a104631cf798b69',
31 u'new_rev': u'd0b2ae0692e722e01d5677f27a104631cf798b69',
32 u'old_rev': u'd0b1ae0692e722e01d5677f27a104631cf798b69',
33 33 u'ref': u'',
34 34 u'total_commits': 2,
35 35 u'type': u'branch'}]
@@ -47,13 +47,17 b' def _pre_push_hook(*args, **kwargs):'
47 47 forbid_files = repo_extra_fields.get('forbid_files_glob', {}).get('field_value')
48 48 forbid_files = aslist(forbid_files)
49 49
50 # forbid_files = ['*'] # example pattern
51
50 52 # optionally get bytes limit for a single file, e.g 1024 for 1KB
51 53 forbid_size_over = repo_extra_fields.get('forbid_size_over', {}).get('field_value')
52 54 forbid_size_over = int(forbid_size_over or 0)
53 55
56 # forbid_size_over = 1024 # example 1024
57
54 58 def validate_file_name_and_size(file_data, forbidden_files=None, size_limit=None):
55 59 """
56 This function validates commited files against some sort of rules.
60 This function validates comited files against some sort of rules.
57 61 It should return a valid boolean, and a reason for failure
58 62
59 63 file_data =[
@@ -87,7 +91,10 b' def _pre_push_hook(*args, **kwargs):'
87 91
88 92 # validate A(dded) files and size
89 93 if size_limit and operation == 'A':
90 size = len(file_data['raw_diff'])
94 if 'file_size' in file_data:
95 size = file_data['file_size']
96 else:
97 size = len(file_data['raw_diff'])
91 98
92 99 reason = 'File {} size of {} bytes exceeds limit {}'.format(
93 100 file_name, format_byte_size_binary(size),
@@ -34,12 +34,51 b' from rhodecode.lib.vcs.backends.hg.diff '
34 34 from rhodecode.lib.vcs.backends.git.diff import GitDiff
35 35
36 36
37 def get_hg_files(repo, refs):
37 def get_svn_files(repo, vcs_repo, refs):
38 txn_id = refs[0]
39 files = []
40 stdout, stderr = vcs_repo.run_svn_command(
41 ['svnlook', 'changed', repo.repo_full_path, '--transaction', txn_id])
42
43 svn_op_to_rc_op = {
44 'A': 'A',
45 'U': 'M',
46 'D': 'D',
47 }
48
49 for entry in stdout.splitlines():
50 parsed_entry = {
51 'raw_diff': '',
52 'filename': '',
53 'chunks': [],
54 'ops': {},
55 'file_size': 0
56 }
57
58 op = entry[0]
59 path = entry[1:].strip()
60
61 rc_op = svn_op_to_rc_op.get(op) or '?'
62 parsed_entry['filename'] = path
63 parsed_entry['operation'] = rc_op
64
65 if rc_op in ['A', 'M']:
66 stdout, stderr = vcs_repo.run_svn_command(
67 ['svnlook', 'filesize', repo.repo_full_path, path, '--transaction', txn_id])
68 file_size = int(stdout.strip())
69 parsed_entry['file_size'] = file_size
70
71 files.append(parsed_entry)
72
73 return files
74
75
76 def get_hg_files(repo, vcs_repo, refs):
38 77 files = []
39 78 return files
40 79
41 80
42 def get_git_files(repo, refs):
81 def get_git_files(repo, vcs_repo, refs):
43 82 files = []
44 83
45 84 for data in refs:
@@ -57,7 +96,7 b' def get_git_files(repo, refs):'
57 96 'diff', old_rev, new_rev
58 97 ]
59 98
60 stdout, stderr = repo.run_git_command(cmd, extra_env=git_env)
99 stdout, stderr = vcs_repo.run_git_command(cmd, extra_env=git_env)
61 100 vcs_diff = GitDiff(stdout)
62 101
63 102 diff_processor = diffs.DiffProcessor(vcs_diff, format='newdiff')
@@ -86,11 +125,14 b' def run(*args, **kwargs):'
86 125 if vcs_type == 'git':
87 126 for rev_data in kwargs['commit_ids']:
88 127 new_environ = dict((k, v) for k, v in rev_data['git_env'])
89 files = get_git_files(vcs_repo, kwargs['commit_ids'])
128 files = get_git_files(repo, vcs_repo, kwargs['commit_ids'])
90 129
91 130 if vcs_type == 'hg':
92 131 for rev_data in kwargs['commit_ids']:
93 132 new_environ = dict((k, v) for k, v in rev_data['hg_env'])
94 files = get_hg_files(vcs_repo, kwargs['commit_ids'])
133 files = get_hg_files(repo, vcs_repo, kwargs['commit_ids'])
134
135 if vcs_type == 'svn':
136 files = get_svn_files(repo, vcs_repo, kwargs['commit_ids'])
95 137
96 138 return files
@@ -402,7 +402,8 b' class RepoIntegrationsView(IntegrationSe'
402 402 c.rhodecode_db_repo = self.repo
403 403 c.repo_name = self.db_repo.repo_name
404 404 c.repository_pull_requests = ScmModel().get_pull_requests(self.repo)
405
405 c.repository_is_user_following = ScmModel().is_following_repo(
406 c.repo_name, self._rhodecode_user.user_id)
406 407 c.has_origin_repo_read_perm = False
407 408 if self.db_repo.fork:
408 409 c.has_origin_repo_read_perm = h.HasRepoPermissionAny(
@@ -92,6 +92,9 b' ACTIONS_V1 = {'
92 92 'repo.commit.comment.delete': {'data': {}},
93 93 'repo.commit.vote': '',
94 94
95 'repo.artifact.add': '',
96 'repo.artifact.delete': '',
97
95 98 'repo_group.create': {'data': {}},
96 99 'repo_group.edit': {'old_data': {}},
97 100 'repo_group.edit.permissions': {},
@@ -2078,8 +2078,7 b' class HasRepoPermissionAny(PermsFunction'
2078 2078 class HasRepoGroupPermissionAny(PermsFunction):
2079 2079 def __call__(self, group_name=None, check_location='', user=None):
2080 2080 self.repo_group_name = group_name
2081 return super(HasRepoGroupPermissionAny, self).__call__(
2082 check_location, user)
2081 return super(HasRepoGroupPermissionAny, self).__call__(check_location, user)
2083 2082
2084 2083 def check_permissions(self, user):
2085 2084 perms = user.permissions
@@ -2095,8 +2094,7 b' class HasRepoGroupPermissionAny(PermsFun'
2095 2094 class HasRepoGroupPermissionAll(PermsFunction):
2096 2095 def __call__(self, group_name=None, check_location='', user=None):
2097 2096 self.repo_group_name = group_name
2098 return super(HasRepoGroupPermissionAll, self).__call__(
2099 check_location, user)
2097 return super(HasRepoGroupPermissionAll, self).__call__(check_location, user)
2100 2098
2101 2099 def check_permissions(self, user):
2102 2100 perms = user.permissions
@@ -2112,8 +2110,7 b' class HasRepoGroupPermissionAll(PermsFun'
2112 2110 class HasUserGroupPermissionAny(PermsFunction):
2113 2111 def __call__(self, user_group_name=None, check_location='', user=None):
2114 2112 self.user_group_name = user_group_name
2115 return super(HasUserGroupPermissionAny, self).__call__(
2116 check_location, user)
2113 return super(HasUserGroupPermissionAny, self).__call__(check_location, user)
2117 2114
2118 2115 def check_permissions(self, user):
2119 2116 perms = user.permissions
@@ -2129,8 +2126,7 b' class HasUserGroupPermissionAny(PermsFun'
2129 2126 class HasUserGroupPermissionAll(PermsFunction):
2130 2127 def __call__(self, user_group_name=None, check_location='', user=None):
2131 2128 self.user_group_name = user_group_name
2132 return super(HasUserGroupPermissionAll, self).__call__(
2133 check_location, user)
2129 return super(HasUserGroupPermissionAll, self).__call__(check_location, user)
2134 2130
2135 2131 def check_permissions(self, user):
2136 2132 perms = user.permissions
@@ -288,7 +288,6 b' def attach_context_attributes(context, r'
288 288 """
289 289 config = request.registry.settings
290 290
291
292 291 rc_config = SettingsModel().get_all_settings(cache=True)
293 292
294 293 context.rhodecode_version = rhodecode.__version__
@@ -375,20 +374,25 b' def attach_context_attributes(context, r'
375 374 "sideside": "sideside"
376 375 }.get(request.GET.get('diffmode'))
377 376
378 if diffmode and diffmode != request.session.get('rc_user_session_attr.diffmode'):
379 request.session['rc_user_session_attr.diffmode'] = diffmode
380
381 # session settings per user
377 is_api = hasattr(request, 'rpc_user')
382 378 session_attrs = {
383 379 # defaults
384 380 "clone_url_format": "http",
385 381 "diffmode": "sideside"
386 382 }
387 for k, v in request.session.items():
388 pref = 'rc_user_session_attr.'
389 if k and k.startswith(pref):
390 k = k[len(pref):]
391 session_attrs[k] = v
383
384 if not is_api:
385 # don't access pyramid session for API calls
386 if diffmode and diffmode != request.session.get('rc_user_session_attr.diffmode'):
387 request.session['rc_user_session_attr.diffmode'] = diffmode
388
389 # session settings per user
390
391 for k, v in request.session.items():
392 pref = 'rc_user_session_attr.'
393 if k and k.startswith(pref):
394 k = k[len(pref):]
395 session_attrs[k] = v
392 396
393 397 context.user_session_attrs = session_attrs
394 398
@@ -420,8 +424,12 b' def attach_context_attributes(context, r'
420 424 'extra': {'plugins': {}}
421 425 }
422 426 # END CONFIG VARS
427 if is_api:
428 csrf_token = None
429 else:
430 csrf_token = auth.get_csrf_token(session=request.session)
423 431
424 context.csrf_token = auth.get_csrf_token(session=request.session)
432 context.csrf_token = csrf_token
425 433 context.backends = rhodecode.BACKENDS.keys()
426 434 context.backends.sort()
427 435 unread_count = 0
@@ -537,7 +545,7 b' def bootstrap_config(request):'
537 545
538 546 # allow pyramid lookup in testing
539 547 config.include('pyramid_mako')
540 config.include('pyramid_beaker')
548 config.include('rhodecode.lib.rc_beaker')
541 549 config.include('rhodecode.lib.rc_cache')
542 550
543 551 add_events_routes(config)
@@ -375,6 +375,27 b' class DbManage(object):'
375 375 hgevolve.ui_active = False
376 376 self.sa.add(hgevolve)
377 377
378 hgevolve = RhodeCodeUi()
379 hgevolve.ui_section = 'experimental'
380 hgevolve.ui_key = 'evolution'
381 hgevolve.ui_value = ''
382 hgevolve.ui_active = False
383 self.sa.add(hgevolve)
384
385 hgevolve = RhodeCodeUi()
386 hgevolve.ui_section = 'experimental'
387 hgevolve.ui_key = 'evolution.exchange'
388 hgevolve.ui_value = ''
389 hgevolve.ui_active = False
390 self.sa.add(hgevolve)
391
392 hgevolve = RhodeCodeUi()
393 hgevolve.ui_section = 'extensions'
394 hgevolve.ui_key = 'topic'
395 hgevolve.ui_value = ''
396 hgevolve.ui_active = False
397 self.sa.add(hgevolve)
398
378 399 # enable hggit disabled by default
379 400 hggit = RhodeCodeUi()
380 401 hggit.ui_section = 'extensions'
@@ -464,9 +485,6 b' class DbManage(object):'
464 485 self.populate_default_permissions()
465 486 return fixed
466 487
467 def update_repo_info(self):
468 RepoModel.update_repoinfo()
469
470 488 def config_prompt(self, test_repo_path='', retries=3):
471 489 defaults = self.cli_args
472 490 _path = defaults.get('repos_location')
@@ -614,7 +614,7 b' class Repository(Base, BaseModel):'
614 614 if (cs_cache != self.changeset_cache or not self.changeset_cache):
615 615 _default = datetime.datetime.fromtimestamp(0)
616 616 last_change = cs_cache.get('date') or _default
617 log.debug('updated repo %s with new cs cache %s', self.repo_name, cs_cache)
617 log.debug('updated repo %s with new commit cache %s', self.repo_name, cs_cache)
618 618 self.updated_on = last_change
619 619 self.changeset_cache = cs_cache
620 620 Session().add(self)
@@ -38,8 +38,6 b' from sqlalchemy.orm import relationship,'
38 38 from sqlalchemy.exc import OperationalError
39 39 from beaker.cache import cache_region, region_invalidate
40 40 from webob.exc import HTTPNotFound
41 from Crypto.Cipher import AES
42 from Crypto import Random
43 41 from zope.cachedescriptors.property import Lazy as LazyProperty
44 42
45 43 from rhodecode.translation import _
@@ -2164,7 +2164,7 b' class Repository(Base, BaseModel):'
2164 2164 if is_outdated(cs_cache) or not self.changeset_cache:
2165 2165 _default = datetime.datetime.fromtimestamp(0)
2166 2166 last_change = cs_cache.get('date') or _default
2167 log.debug('updated repo %s with new cs cache %s',
2167 log.debug('updated repo %s with new commit cache %s',
2168 2168 self.repo_name, cs_cache)
2169 2169 self.updated_on = last_change
2170 2170 self.changeset_cache = cs_cache
@@ -2230,7 +2230,7 b' class Repository(Base, BaseModel):'
2230 2230 if is_outdated(cs_cache) or not self.changeset_cache:
2231 2231 _default = datetime.datetime.fromtimestamp(0)
2232 2232 last_change = cs_cache.get('date') or _default
2233 log.debug('updated repo %s with new cs cache %s',
2233 log.debug('updated repo %s with new commit cache %s',
2234 2234 self.repo_name, cs_cache)
2235 2235 self.updated_on = last_change
2236 2236 self.changeset_cache = cs_cache
@@ -2278,7 +2278,7 b' class Repository(Base, BaseModel):'
2278 2278 # if yes, we use the current timestamp instead. Imagine you get
2279 2279 # old commit pushed 1y ago, we'd set last update 1y to ago.
2280 2280 last_change = _default
2281 log.debug('updated repo %s with new cs cache %s',
2281 log.debug('updated repo %s with new commit cache %s',
2282 2282 self.repo_name, cs_cache)
2283 2283 self.updated_on = last_change
2284 2284 self.changeset_cache = cs_cache
@@ -2301,7 +2301,7 b' class Repository(Base, BaseModel):'
2301 2301 # if yes, we use the current timestamp instead. Imagine you get
2302 2302 # old commit pushed 1y ago, we'd set last update 1y to ago.
2303 2303 last_change = _default
2304 log.debug('updated repo %s with new cs cache %s',
2304 log.debug('updated repo %s with new commit cache %s',
2305 2305 self.repo_name, cs_cache)
2306 2306 self.updated_on = last_change
2307 2307 self.changeset_cache = cs_cache
@@ -2301,7 +2301,7 b' class Repository(Base, BaseModel):'
2301 2301 # if yes, we use the current timestamp instead. Imagine you get
2302 2302 # old commit pushed 1y ago, we'd set last update 1y to ago.
2303 2303 last_change = _default
2304 log.debug('updated repo %s with new cs cache %s',
2304 log.debug('updated repo %s with new commit cache %s',
2305 2305 self.repo_name, cs_cache)
2306 2306 self.updated_on = last_change
2307 2307 self.changeset_cache = cs_cache
@@ -1865,7 +1865,7 b' class Repository(Base, BaseModel):'
1865 1865 if is_outdated(cs_cache) or not self.changeset_cache:
1866 1866 _default = datetime.datetime.fromtimestamp(0)
1867 1867 last_change = cs_cache.get('date') or _default
1868 log.debug('updated repo %s with new cs cache %s',
1868 log.debug('updated repo %s with new commit cache %s',
1869 1869 self.repo_name, cs_cache)
1870 1870 self.updated_on = last_change
1871 1871 self.changeset_cache = cs_cache
@@ -1868,7 +1868,7 b' class Repository(Base, BaseModel):'
1868 1868 if is_outdated(cs_cache) or not self.changeset_cache:
1869 1869 _default = datetime.datetime.fromtimestamp(0)
1870 1870 last_change = cs_cache.get('date') or _default
1871 log.debug('updated repo %s with new cs cache %s',
1871 log.debug('updated repo %s with new commit cache %s',
1872 1872 self.repo_name, cs_cache)
1873 1873 self.updated_on = last_change
1874 1874 self.changeset_cache = cs_cache
@@ -1867,7 +1867,7 b' class Repository(Base, BaseModel):'
1867 1867 if is_outdated(cs_cache) or not self.changeset_cache:
1868 1868 _default = datetime.datetime.fromtimestamp(0)
1869 1869 last_change = cs_cache.get('date') or _default
1870 log.debug('updated repo %s with new cs cache %s',
1870 log.debug('updated repo %s with new commit cache %s',
1871 1871 self.repo_name, cs_cache)
1872 1872 self.updated_on = last_change
1873 1873 self.changeset_cache = cs_cache
@@ -1869,7 +1869,7 b' class Repository(Base, BaseModel):'
1869 1869 if is_outdated(cs_cache) or not self.changeset_cache:
1870 1870 _default = datetime.datetime.fromtimestamp(0)
1871 1871 last_change = cs_cache.get('date') or _default
1872 log.debug('updated repo %s with new cs cache %s',
1872 log.debug('updated repo %s with new commit cache %s',
1873 1873 self.repo_name, cs_cache)
1874 1874 self.updated_on = last_change
1875 1875 self.changeset_cache = cs_cache
@@ -1869,7 +1869,7 b' class Repository(Base, BaseModel):'
1869 1869 if is_outdated(cs_cache) or not self.changeset_cache:
1870 1870 _default = datetime.datetime.fromtimestamp(0)
1871 1871 last_change = cs_cache.get('date') or _default
1872 log.debug('updated repo %s with new cs cache %s',
1872 log.debug('updated repo %s with new commit cache %s',
1873 1873 self.repo_name, cs_cache)
1874 1874 self.updated_on = last_change
1875 1875 self.changeset_cache = cs_cache
@@ -1912,7 +1912,7 b' class Repository(Base, BaseModel):'
1912 1912 if is_outdated(cs_cache) or not self.changeset_cache:
1913 1913 _default = datetime.datetime.fromtimestamp(0)
1914 1914 last_change = cs_cache.get('date') or _default
1915 log.debug('updated repo %s with new cs cache %s',
1915 log.debug('updated repo %s with new commit cache %s',
1916 1916 self.repo_name, cs_cache)
1917 1917 self.updated_on = last_change
1918 1918 self.changeset_cache = cs_cache
@@ -1913,7 +1913,7 b' class Repository(Base, BaseModel):'
1913 1913 if is_outdated(cs_cache) or not self.changeset_cache:
1914 1914 _default = datetime.datetime.fromtimestamp(0)
1915 1915 last_change = cs_cache.get('date') or _default
1916 log.debug('updated repo %s with new cs cache %s',
1916 log.debug('updated repo %s with new commit cache %s',
1917 1917 self.repo_name, cs_cache)
1918 1918 self.updated_on = last_change
1919 1919 self.changeset_cache = cs_cache
@@ -2100,7 +2100,7 b' class Repository(Base, BaseModel):'
2100 2100 if is_outdated(cs_cache) or not self.changeset_cache:
2101 2101 _default = datetime.datetime.fromtimestamp(0)
2102 2102 last_change = cs_cache.get('date') or _default
2103 log.debug('updated repo %s with new cs cache %s',
2103 log.debug('updated repo %s with new commit cache %s',
2104 2104 self.repo_name, cs_cache)
2105 2105 self.updated_on = last_change
2106 2106 self.changeset_cache = cs_cache
@@ -111,4 +111,28 b' class AESCipher(object):'
111 111
112 112 @staticmethod
113 113 def _unpad(s):
114 return s[:-ord(s[len(s)-1:])] No newline at end of file
114 return s[:-ord(s[len(s)-1:])]
115
116
117 def validate_and_get_enc_data(enc_data, enc_key, enc_strict_mode):
118 parts = enc_data.split('$', 3)
119 if not len(parts) == 3:
120 # probably not encrypted values
121 return enc_data
122 else:
123 if parts[0] != 'enc':
124 # parts ok but without our header ?
125 return enc_data
126
127 # at that stage we know it's our encryption
128 if parts[1] == 'aes':
129 decrypted_data = AESCipher(enc_key).decrypt(parts[2])
130 elif parts[1] == 'aes_hmac':
131 decrypted_data = AESCipher(
132 enc_key, hmac=True,
133 strict_verification=enc_strict_mode).decrypt(parts[2])
134 else:
135 raise ValueError(
136 'Encryption type part is wrong, must be `aes` '
137 'or `aes_hmac`, got `%s` instead' % (parts[1]))
138 return decrypted_data
@@ -199,6 +199,7 b' class _GetError(object):'
199 199 if form_errors and field_name in form_errors:
200 200 return literal(tmpl % form_errors.get(field_name))
201 201
202
202 203 get_error = _GetError()
203 204
204 205
@@ -214,38 +215,45 b' class _ToolTip(object):'
214 215 tooltip_title = escape(tooltip_title)
215 216 tooltip_title = tooltip_title.replace('<', '&lt;').replace('>', '&gt;')
216 217 return tooltip_title
218
219
217 220 tooltip = _ToolTip()
218 221
222 files_icon = u'<i class="file-breadcrumb-copy tooltip icon-clipboard clipboard-action" data-clipboard-text="{}" title="Copy the full path"></i>'
219 223
220 def files_breadcrumbs(repo_name, commit_id, file_path):
224
225 def files_breadcrumbs(repo_name, commit_id, file_path, at_ref=None, limit_items=False, linkify_last_item=False):
221 226 if isinstance(file_path, str):
222 227 file_path = safe_unicode(file_path)
223 228
224 # TODO: johbo: Is this always a url like path, or is this operating
225 # system dependent?
226 path_segments = file_path.split('/')
229 route_qry = {'at': at_ref} if at_ref else None
227 230
228 repo_name_html = escape(repo_name)
229 if len(path_segments) == 1 and path_segments[0] == '':
230 url_segments = [repo_name_html]
231 else:
232 url_segments = [
233 link_to(
234 repo_name_html,
235 route_path(
236 'repo_files',
237 repo_name=repo_name,
238 commit_id=commit_id,
239 f_path=''),
240 class_='pjax-link')]
231 # first segment is a `..` link to repo files
232 root_name = literal(u'<i class="icon-home"></i>')
233 url_segments = [
234 link_to(
235 root_name,
236 route_path(
237 'repo_files',
238 repo_name=repo_name,
239 commit_id=commit_id,
240 f_path='',
241 _query=route_qry),
242 )]
241 243
244 path_segments = file_path.split('/')
242 245 last_cnt = len(path_segments) - 1
243 246 for cnt, segment in enumerate(path_segments):
244 247 if not segment:
245 248 continue
246 249 segment_html = escape(segment)
247 250
248 if cnt != last_cnt:
251 last_item = cnt == last_cnt
252
253 if last_item and linkify_last_item is False:
254 # plain version
255 url_segments.append(segment_html)
256 else:
249 257 url_segments.append(
250 258 link_to(
251 259 segment_html,
@@ -253,12 +261,32 b' def files_breadcrumbs(repo_name, commit_'
253 261 'repo_files',
254 262 repo_name=repo_name,
255 263 commit_id=commit_id,
256 f_path='/'.join(path_segments[:cnt + 1])),
257 class_='pjax-link'))
258 else:
259 url_segments.append(segment_html)
264 f_path='/'.join(path_segments[:cnt + 1]),
265 _query=route_qry),
266 ))
267
268 limited_url_segments = url_segments[:1] + ['...'] + url_segments[-5:]
269 if limit_items and len(limited_url_segments) < len(url_segments):
270 url_segments = limited_url_segments
260 271
261 return literal('/'.join(url_segments))
272 full_path = file_path
273 icon = files_icon.format(escape(full_path))
274 if file_path == '':
275 return root_name
276 else:
277 return literal(' / '.join(url_segments) + icon)
278
279
280 def files_url_data(request):
281 matchdict = request.matchdict
282
283 if 'f_path' not in matchdict:
284 matchdict['f_path'] = ''
285
286 if 'commit_id' not in matchdict:
287 matchdict['commit_id'] = 'tip'
288
289 return json.dumps(matchdict)
262 290
263 291
264 292 def code_highlight(code, lexer, formatter, use_hl_filter=False):
@@ -1196,7 +1224,7 b' class InitialsGravatar(object):'
1196 1224 </text>
1197 1225 </svg>""".format(
1198 1226 size=self.size,
1199 f_size=self.size/1.85, # scale the text inside the box nicely
1227 f_size=self.size/2.05, # scale the text inside the box nicely
1200 1228 background=self.background,
1201 1229 text_color=self.text_color,
1202 1230 text=initials.upper(),
@@ -1486,10 +1514,12 b' def breadcrumb_repo_link(repo):'
1486 1514 """
1487 1515
1488 1516 path = [
1489 link_to(group.name, route_path('repo_group_home', repo_group_name=group.group_name))
1517 link_to(group.name, route_path('repo_group_home', repo_group_name=group.group_name),
1518 title='last change:{}'.format(format_date(group.last_commit_change)))
1490 1519 for group in repo.groups_with_parents
1491 1520 ] + [
1492 link_to(repo.just_name, route_path('repo_summary', repo_name=repo.repo_name))
1521 link_to(repo.just_name, route_path('repo_summary', repo_name=repo.repo_name),
1522 title='last change:{}'.format(format_date(repo.last_commit_change)))
1493 1523 ]
1494 1524
1495 1525 return literal(' &raquo; '.join(path))
@@ -1507,11 +1537,13 b' def breadcrumb_repo_group_link(repo_grou'
1507 1537
1508 1538 path = [
1509 1539 link_to(group.name,
1510 route_path('repo_group_home', repo_group_name=group.group_name))
1540 route_path('repo_group_home', repo_group_name=group.group_name),
1541 title='last change:{}'.format(format_date(group.last_commit_change)))
1511 1542 for group in repo_group.parents
1512 1543 ] + [
1513 1544 link_to(repo_group.name,
1514 route_path('repo_group_home', repo_group_name=repo_group.group_name))
1545 route_path('repo_group_home', repo_group_name=repo_group.group_name),
1546 title='last change:{}'.format(format_date(repo_group.last_commit_change)))
1515 1547 ]
1516 1548
1517 1549 return literal(' &raquo; '.join(path))
@@ -1907,23 +1939,26 b' def secure_form(form_url, method="POST",'
1907 1939
1908 1940 def dropdownmenu(name, selected, options, enable_filter=False, **attrs):
1909 1941 select_html = select(name, selected, options, **attrs)
1942
1910 1943 select2 = """
1911 1944 <script>
1912 1945 $(document).ready(function() {
1913 1946 $('#%s').select2({
1914 containerCssClass: 'drop-menu',
1947 containerCssClass: 'drop-menu %s',
1915 1948 dropdownCssClass: 'drop-menu-dropdown',
1916 1949 dropdownAutoWidth: true%s
1917 1950 });
1918 1951 });
1919 1952 </script>
1920 1953 """
1954
1921 1955 filter_option = """,
1922 1956 minimumResultsForSearch: -1
1923 1957 """
1924 1958 input_id = attrs.get('id') or name
1959 extra_classes = ' '.join(attrs.pop('extra_classes', []))
1925 1960 filter_enabled = "" if enable_filter else filter_option
1926 select_script = literal(select2 % (input_id, filter_enabled))
1961 select_script = literal(select2 % (input_id, extra_classes, filter_enabled))
1927 1962
1928 1963 return literal(select_html+select_script)
1929 1964
@@ -1944,7 +1979,7 b' def get_visual_attr(tmpl_context_var, at'
1944 1979
1945 1980 def get_last_path_part(file_node):
1946 1981 if not file_node.path:
1947 return u''
1982 return u'/'
1948 1983
1949 1984 path = safe_unicode(file_node.path.split('/')[-1])
1950 1985 return u'../' + path
@@ -2033,10 +2068,11 b' def reviewer_as_json(*args, **kwargs):'
2033 2068 def get_repo_view_type(request):
2034 2069 route_name = request.matched_route.name
2035 2070 route_to_view_type = {
2036 'repo_changelog': 'changelog',
2071 'repo_changelog': 'commits',
2072 'repo_commits': 'commits',
2037 2073 'repo_files': 'files',
2038 2074 'repo_summary': 'summary',
2039 2075 'repo_commit': 'commit'
2076 }
2040 2077
2041 }
2042 2078 return route_to_view_type.get(route_name)
@@ -80,7 +80,7 b' def trigger_log_create_pull_request_hook'
80 80 extras = _get_rc_scm_extras(username, repo_name, repo_alias,
81 81 'create_pull_request')
82 82 events.trigger(events.PullRequestCreateEvent(pull_request))
83 extras.update(pull_request.get_api_data())
83 extras.update(pull_request.get_api_data(with_merge_state=False))
84 84 hooks_base.log_create_pull_request(**extras)
85 85
86 86
@@ -80,6 +80,13 b' class BaseSearcher(object):'
80 80 def extract_search_tags(query):
81 81 return []
82 82
83 @staticmethod
84 def escape_specials(val):
85 """
86 Handle and escape reserved chars for search
87 """
88 return val
89
83 90
84 91 def search_config(config, prefix='search.'):
85 92 _config = {}
@@ -20,7 +20,55 b''
20 20
21 21 import markdown
22 22
23 from mdx_gfm import GithubFlavoredMarkdownExtension # pragma: no cover
23 from markdown.extensions import Extension
24 from markdown.extensions.fenced_code import FencedCodeExtension
25 from markdown.extensions.smart_strong import SmartEmphasisExtension
26 from markdown.extensions.tables import TableExtension
27 from markdown.extensions.nl2br import Nl2BrExtension
28
29 import gfm
30
31
32 class GithubFlavoredMarkdownExtension(Extension):
33 """
34 An extension that is as compatible as possible with GitHub-flavored
35 Markdown (GFM).
36
37 This extension aims to be compatible with the variant of GFM that GitHub
38 uses for Markdown-formatted gists and files (including READMEs). This
39 variant seems to have all the extensions described in the `GFM
40 documentation`_, except:
41
42 - Newlines in paragraphs are not transformed into ``br`` tags.
43 - Intra-GitHub links to commits, repositories, and issues are not
44 supported.
45
46 If you need support for features specific to GitHub comments and issues,
47 please use :class:`mdx_gfm.GithubFlavoredMarkdownExtension`.
48
49 .. _GFM documentation: https://guides.github.com/features/mastering-markdown/
50 """
51
52 def extendMarkdown(self, md, md_globals):
53 # Built-in extensions
54 FencedCodeExtension().extendMarkdown(md, md_globals)
55 SmartEmphasisExtension().extendMarkdown(md, md_globals)
56 TableExtension().extendMarkdown(md, md_globals)
57
58 # Custom extensions
59 gfm.AutolinkExtension().extendMarkdown(md, md_globals)
60 gfm.AutomailExtension().extendMarkdown(md, md_globals)
61 gfm.HiddenHiliteExtension([
62 ('guess_lang', 'False'),
63 ('css_class', 'highlight')
64 ]).extendMarkdown(md, md_globals)
65 gfm.SemiSaneListExtension().extendMarkdown(md, md_globals)
66 gfm.SpacedLinkExtension().extendMarkdown(md, md_globals)
67 gfm.StrikethroughExtension().extendMarkdown(md, md_globals)
68 gfm.TaskListExtension([
69 ('list_attrs', {'class': 'checkbox'})
70 ]).extendMarkdown(md, md_globals)
71 Nl2BrExtension().extendMarkdown(md, md_globals)
24 72
25 73
26 74 # Global Vars
@@ -500,38 +500,38 b' class MarkupRenderer(object):'
500 500 (body, resources) = html_exporter.from_notebook_node(notebook)
501 501 header = '<!-- ## IPYTHON NOTEBOOK RENDERING ## -->'
502 502 js = MakoTemplate(r'''
503 <!-- Load mathjax -->
504 <!-- MathJax configuration -->
505 <script type="text/x-mathjax-config">
506 MathJax.Hub.Config({
507 jax: ["input/TeX","output/HTML-CSS", "output/PreviewHTML"],
508 extensions: ["tex2jax.js","MathMenu.js","MathZoom.js", "fast-preview.js", "AssistiveMML.js", "[Contrib]/a11y/accessibility-menu.js"],
509 TeX: {
510 extensions: ["AMSmath.js","AMSsymbols.js","noErrors.js","noUndefined.js"]
511 },
512 tex2jax: {
513 inlineMath: [ ['$','$'], ["\\(","\\)"] ],
514 displayMath: [ ['$$','$$'], ["\\[","\\]"] ],
515 processEscapes: true,
516 processEnvironments: true
517 },
518 // Center justify equations in code and markdown cells. Elsewhere
519 // we use CSS to left justify single line equations in code cells.
520 displayAlign: 'center',
521 "HTML-CSS": {
522 styles: {'.MathJax_Display': {"margin": 0}},
523 linebreaks: { automatic: true },
524 availableFonts: ["STIX", "TeX"]
525 },
526 showMathMenu: false
527 });
528 </script>
529 <!-- End of mathjax configuration -->
530 <script src="${h.asset('js/src/math_jax/MathJax.js')}"></script>
503 <!-- MathJax configuration -->
504 <script type="text/x-mathjax-config">
505 MathJax.Hub.Config({
506 jax: ["input/TeX","output/HTML-CSS", "output/PreviewHTML"],
507 extensions: ["tex2jax.js","MathMenu.js","MathZoom.js", "fast-preview.js", "AssistiveMML.js", "[Contrib]/a11y/accessibility-menu.js"],
508 TeX: {
509 extensions: ["AMSmath.js","AMSsymbols.js","noErrors.js","noUndefined.js"]
510 },
511 tex2jax: {
512 inlineMath: [ ['$','$'], ["\\(","\\)"] ],
513 displayMath: [ ['$$','$$'], ["\\[","\\]"] ],
514 processEscapes: true,
515 processEnvironments: true
516 },
517 // Center justify equations in code and markdown cells. Elsewhere
518 // we use CSS to left justify single line equations in code cells.
519 displayAlign: 'center',
520 "HTML-CSS": {
521 styles: {'.MathJax_Display': {"margin": 0}},
522 linebreaks: { automatic: true },
523 availableFonts: ["STIX", "TeX"]
524 },
525 showMathMenu: false
526 });
527 </script>
528 <!-- End of MathJax configuration -->
529 <script src="${h.asset('js/src/math_jax/MathJax.js')}"></script>
531 530 ''').render(h=helpers)
532 531
533 css = '<style>{}</style>'.format(
534 ''.join(_sanitize_resources(resources['inlining']['css'])))
532 css = MakoTemplate(r'''
533 <link rel="stylesheet" type="text/css" href="${h.asset('css/style-ipython.css', ver=ver)}" media="screen"/>
534 ''').render(h=helpers, ver='ver1')
535 535
536 536 body = '\n'.join([header, css, js, body])
537 537 return body, resources
@@ -142,7 +142,7 b' class SimpleGit(simplevcs.SimpleVCS):'
142 142 return self.scm_app.create_git_wsgi_app(
143 143 repo_path, repo_name, config)
144 144
145 def _create_config(self, extras, repo_name):
145 def _create_config(self, extras, repo_name, scheme='http'):
146 146 extras['git_update_server_info'] = utils2.str2bool(
147 147 rhodecode.CONFIG.get('git_update_server_info'))
148 148
@@ -152,4 +152,5 b' class SimpleGit(simplevcs.SimpleVCS):'
152 152 extras['git_lfs_enabled'] = utils2.str2bool(
153 153 config.get('vcs_git_lfs', 'enabled'))
154 154 extras['git_lfs_store_path'] = custom_store or default_lfs_store()
155 extras['git_lfs_http_scheme'] = scheme
155 156 return extras
@@ -153,7 +153,7 b' class SimpleHg(simplevcs.SimpleVCS):'
153 153 def _create_wsgi_app(self, repo_path, repo_name, config):
154 154 return self.scm_app.create_hg_wsgi_app(repo_path, repo_name, config)
155 155
156 def _create_config(self, extras, repo_name):
156 def _create_config(self, extras, repo_name, scheme='http'):
157 157 config = utils.make_db_config(repo=repo_name)
158 158 config.set('rhodecode', 'RC_SCM_DATA', json.dumps(extras))
159 159
@@ -87,20 +87,22 b' class SimpleSvnApp(object):'
87 87 stream = True
88 88
89 89 stream = stream
90 log.debug(
91 'Calling SVN PROXY: method:%s via `%s`, Stream: %s',
92 req_method, path_info, stream)
93 response = requests.request(
94 req_method, path_info,
95 data=data, headers=request_headers, stream=stream)
90 log.debug('Calling SVN PROXY at `%s`, using method:%s. Stream: %s',
91 path_info, req_method, stream)
92 try:
93 response = requests.request(
94 req_method, path_info,
95 data=data, headers=request_headers, stream=stream)
96 except requests.ConnectionError:
97 log.exception('ConnectionError occurred for endpoint %s', path_info)
98 raise
96 99
97 100 if response.status_code not in [200, 401]:
101 text = '\n{}'.format(response.text) if response.text else ''
98 102 if response.status_code >= 500:
99 log.error('Got SVN response:%s with text:\n`%s`',
100 response, response.text)
103 log.error('Got SVN response:%s with text:`%s`', response, text)
101 104 else:
102 log.debug('Got SVN response:%s with text:\n`%s`',
103 response, response.text)
105 log.debug('Got SVN response:%s with text:`%s`', response, text)
104 106 else:
105 107 log.debug('got response code: %s', response.status_code)
106 108
@@ -217,7 +219,7 b' class SimpleSvn(simplevcs.SimpleVCS):'
217 219 conf = self.repo_vcs_config
218 220 return str2bool(conf.get('vcs_svn_proxy', 'http_requests_enabled'))
219 221
220 def _create_config(self, extras, repo_name):
222 def _create_config(self, extras, repo_name, scheme='http'):
221 223 conf = self.repo_vcs_config
222 224 server_url = conf.get('vcs_svn_proxy', 'http_server_url')
223 225 server_url = server_url or self.DEFAULT_HTTP_SERVER
@@ -360,6 +360,13 b' class SimpleVCS(object):'
360 360
361 361 return perm_result
362 362
363 def _get_http_scheme(self, environ):
364 try:
365 return environ['wsgi.url_scheme']
366 except Exception:
367 log.exception('Failed to read http scheme')
368 return 'http'
369
363 370 def _check_ssl(self, environ, start_response):
364 371 """
365 372 Checks the SSL check flag and returns False if SSL is not present
@@ -597,7 +604,9 b' class SimpleVCS(object):'
597 604 extras, environ, action, txn_id=txn_id)
598 605 log.debug('HOOKS extras is %s', extras)
599 606
600 config = self._create_config(extras, self.acl_repo_name)
607 http_scheme = self._get_http_scheme(environ)
608
609 config = self._create_config(extras, self.acl_repo_name, scheme=http_scheme)
601 610 app = self._create_wsgi_app(repo_path, self.url_repo_name, config)
602 611 with callback_daemon:
603 612 app.rc_extras = extras
@@ -643,7 +652,7 b' class SimpleVCS(object):'
643 652 """Return the WSGI app that will finally handle the request."""
644 653 raise NotImplementedError()
645 654
646 def _create_config(self, extras, repo_name):
655 def _create_config(self, extras, repo_name, scheme='http'):
647 656 """Create a safe config representation."""
648 657 raise NotImplementedError()
649 658
@@ -23,6 +23,7 b' import re'
23 23 import time
24 24 import datetime
25 25 import dateutil
26 import pickle
26 27
27 28 from rhodecode.model.db import DbSession, Session
28 29
@@ -142,7 +143,6 b' class FileAuthSessions(BaseAuthSessions)'
142 143 return stats['callbacks']
143 144
144 145
145
146 146 class MemcachedAuthSessions(BaseAuthSessions):
147 147 SESSION_TYPE = 'ext:memcached'
148 148 _key_regex = re.compile(r'ITEM (.*_session) \[(.*); (.*)\]')
@@ -195,6 +195,43 b' class MemcachedAuthSessions(BaseAuthSess'
195 195 raise CleanupCommand('Cleanup for this session type not yet available')
196 196
197 197
198 class RedisAuthSessions(BaseAuthSessions):
199 SESSION_TYPE = 'ext:redis'
200
201 def _get_client(self):
202 import redis
203 args = {
204 'socket_timeout': 60,
205 'url': self.config.get('beaker.session.url')
206 }
207
208 client = redis.StrictRedis.from_url(**args)
209 return client
210
211 def get_count(self):
212 client = self._get_client()
213 return len(client.keys('beaker_cache:*'))
214
215 def get_expired_count(self, older_than_seconds=None):
216 expiry_date = self._seconds_to_date(older_than_seconds)
217 return self.NOT_AVAILABLE
218
219 def clean_sessions(self, older_than_seconds=None):
220 client = self._get_client()
221 expiry_time = time.time() - older_than_seconds
222 deleted_keys = 0
223 for key in client.keys('beaker_cache:*'):
224 data = client.get(key)
225 if data:
226 json_data = pickle.loads(data)
227 accessed_time = json_data['_accessed_time']
228 if accessed_time < expiry_time:
229 client.delete(key)
230 deleted_keys += 1
231
232 return deleted_keys
233
234
198 235 class MemoryAuthSessions(BaseAuthSessions):
199 236 SESSION_TYPE = 'memory'
200 237
@@ -212,6 +249,7 b' def get_session_handler(session_type):'
212 249 types = {
213 250 'file': FileAuthSessions,
214 251 'ext:memcached': MemcachedAuthSessions,
252 'ext:redis': RedisAuthSessions,
215 253 'ext:database': DbAuthSessions,
216 254 'memory': MemoryAuthSessions
217 255 }
@@ -371,7 +371,8 b' def config_data_from_db(clear_session=Tr'
371 371 config.append((
372 372 safe_str(setting.section), safe_str(setting.key), False))
373 373 log.debug(
374 'settings ui from db: %s',
374 'settings ui from db@repo[%s]: %s',
375 repo,
375 376 ','.join(map(lambda s: '[{}] {}={}'.format(*s), ui_data)))
376 377 if clear_session:
377 378 meta.Session.remove()
@@ -33,6 +33,8 b' import collections'
33 33 import warnings
34 34
35 35 from zope.cachedescriptors.property import Lazy as LazyProperty
36 from zope.cachedescriptors.property import CachedProperty
37
36 38 from pyramid import compat
37 39
38 40 from rhodecode.translation import lazy_ugettext
@@ -53,6 +55,7 b' log = logging.getLogger(__name__)'
53 55
54 56 FILEMODE_DEFAULT = 0o100644
55 57 FILEMODE_EXECUTABLE = 0o100755
58 EMPTY_COMMIT_ID = '0' * 40
56 59
57 60 Reference = collections.namedtuple('Reference', ('type', 'name', 'commit_id'))
58 61
@@ -161,7 +164,7 b' class MergeResponse(object):'
161 164 u'This pull request cannot be merged because the source contains '
162 165 u'more branches than the target.'),
163 166 MergeFailureReason.HG_TARGET_HAS_MULTIPLE_HEADS: lazy_ugettext(
164 u'This pull request cannot be merged because the target '
167 u'This pull request cannot be merged because the target `{target_ref.name}` '
165 168 u'has multiple heads: `{heads}`.'),
166 169 MergeFailureReason.TARGET_IS_LOCKED: lazy_ugettext(
167 170 u'This pull request cannot be merged because the target repository is '
@@ -261,6 +264,7 b' class BaseRepository(object):'
261 264 EMPTY_COMMIT_ID = '0' * 40
262 265
263 266 path = None
267 _commit_ids_ver = 0
264 268
265 269 def __init__(self, repo_path, config=None, create=False, **kwargs):
266 270 """
@@ -309,6 +313,9 b' class BaseRepository(object):'
309 313 def _remote(self):
310 314 raise NotImplementedError
311 315
316 def _heads(self, branch=None):
317 return []
318
312 319 @LazyProperty
313 320 def EMPTY_COMMIT(self):
314 321 return EmptyCommit(self.EMPTY_COMMIT_ID)
@@ -380,7 +387,7 b' class BaseRepository(object):'
380 387 return commit.size
381 388
382 389 def is_empty(self):
383 return not bool(self.commit_ids)
390 return self._remote.is_empty()
384 391
385 392 @staticmethod
386 393 def check_url(url, config):
@@ -401,6 +408,15 b' class BaseRepository(object):'
401 408 # COMMITS
402 409 # ==========================================================================
403 410
411 @CachedProperty('_commit_ids_ver')
412 def commit_ids(self):
413 raise NotImplementedError
414
415 def append_commit_id(self, commit_id):
416 if commit_id not in self.commit_ids:
417 self._rebuild_cache(self.commit_ids + [commit_id])
418 self._commit_ids_ver = time.time()
419
404 420 def get_commit(self, commit_id=None, commit_idx=None, pre_load=None, translate_tag=None):
405 421 """
406 422 Returns instance of `BaseCommit` class. If `commit_id` and `commit_idx`
@@ -1091,12 +1107,12 b' class BaseCommit(object):'
1091 1107 """
1092 1108 return None
1093 1109
1094 def archive_repo(self, file_path, kind='tgz', subrepos=None,
1095 prefix=None, write_metadata=False, mtime=None):
1110 def archive_repo(self, archive_dest_path, kind='tgz', subrepos=None,
1111 prefix=None, write_metadata=False, mtime=None, archive_at_path='/'):
1096 1112 """
1097 1113 Creates an archive containing the contents of the repository.
1098 1114
1099 :param file_path: path to the file which to create the archive.
1115 :param archive_dest_path: path to the file which to create the archive.
1100 1116 :param kind: one of following: ``"tbz2"``, ``"tgz"``, ``"zip"``.
1101 1117 :param prefix: name of root directory in archive.
1102 1118 Default is repository name and commit's short_id joined with dash:
@@ -1104,10 +1120,11 b' class BaseCommit(object):'
1104 1120 :param write_metadata: write a metadata file into archive.
1105 1121 :param mtime: custom modification time for archive creation, defaults
1106 1122 to time.time() if not given.
1123 :param archive_at_path: pack files at this path (default '/')
1107 1124
1108 1125 :raise VCSError: If prefix has a problem.
1109 1126 """
1110 allowed_kinds = settings.ARCHIVE_SPECS.keys()
1127 allowed_kinds = [x[0] for x in settings.ARCHIVE_SPECS]
1111 1128 if kind not in allowed_kinds:
1112 1129 raise ImproperArchiveTypeError(
1113 1130 'Archive kind (%s) not supported use one of %s' %
@@ -1115,11 +1132,11 b' class BaseCommit(object):'
1115 1132
1116 1133 prefix = self._validate_archive_prefix(prefix)
1117 1134
1118 mtime = mtime or time.mktime(self.date.timetuple())
1135 mtime = mtime is not None or time.mktime(self.date.timetuple())
1119 1136
1120 1137 file_info = []
1121 1138 cur_rev = self.repository.get_commit(commit_id=self.raw_id)
1122 for _r, _d, files in cur_rev.walk('/'):
1139 for _r, _d, files in cur_rev.walk(archive_at_path):
1123 1140 for f in files:
1124 1141 f_path = os.path.join(prefix, f.path)
1125 1142 file_info.append(
@@ -1128,15 +1145,15 b' class BaseCommit(object):'
1128 1145 if write_metadata:
1129 1146 metadata = [
1130 1147 ('repo_name', self.repository.name),
1131 ('rev', self.raw_id),
1132 ('create_time', mtime),
1148 ('commit_id', self.raw_id),
1149 ('mtime', mtime),
1133 1150 ('branch', self.branch),
1134 1151 ('tags', ','.join(self.tags)),
1135 1152 ]
1136 1153 meta = ["%s:%s" % (f_name, value) for f_name, value in metadata]
1137 1154 file_info.append(('.archival.txt', 0o644, False, '\n'.join(meta)))
1138 1155
1139 connection.Hg.archive_repo(file_path, mtime, file_info, kind)
1156 connection.Hg.archive_repo(archive_dest_path, mtime, file_info, kind)
1140 1157
1141 1158 def _validate_archive_prefix(self, prefix):
1142 1159 if prefix is None:
@@ -1505,9 +1522,7 b' class BaseInMemoryCommit(object):'
1505 1522 "Cannot remove node at %s from "
1506 1523 "following parents: %s" % (not_removed, parents))
1507 1524
1508 def commit(
1509 self, message, author, parents=None, branch=None, date=None,
1510 **kwargs):
1525 def commit(self, message, author, parents=None, branch=None, date=None, **kwargs):
1511 1526 """
1512 1527 Performs in-memory commit (doesn't check workdir in any way) and
1513 1528 returns newly created :class:`BaseCommit`. Updates repository's
@@ -1555,7 +1570,7 b' class EmptyCommit(BaseCommit):'
1555 1570 """
1556 1571
1557 1572 def __init__(
1558 self, commit_id='0' * 40, repo=None, alias=None, idx=-1,
1573 self, commit_id=EMPTY_COMMIT_ID, repo=None, alias=None, idx=-1,
1559 1574 message='', author='', date=None):
1560 1575 self._empty_commit_id = commit_id
1561 1576 # TODO: johbo: Solve idx parameter, default value does not make
@@ -1615,7 +1630,7 b' class EmptyChangeset(EmptyCommit):'
1615 1630 "Use EmptyCommit instead of EmptyChangeset", DeprecationWarning)
1616 1631 return super(EmptyCommit, cls).__new__(cls, *args, **kwargs)
1617 1632
1618 def __init__(self, cs='0' * 40, repo=None, requested_revision=None,
1633 def __init__(self, cs=EMPTY_COMMIT_ID, repo=None, requested_revision=None,
1619 1634 alias=None, revision=-1, message='', author='', date=None):
1620 1635 if requested_revision is not None:
1621 1636 warnings.warn(
@@ -234,8 +234,7 b' class GitCommit(base.BaseCommit):'
234 234 path = self._fix_path(path)
235 235 if self._get_kind(path) != NodeKind.FILE:
236 236 raise CommitError(
237 "File does not exist for commit %s at '%s'" %
238 (self.raw_id, path))
237 "File does not exist for commit %s at '%s'" % (self.raw_id, path))
239 238 return path
240 239
241 240 def _get_file_nodes(self):
@@ -353,8 +352,7 b' class GitCommit(base.BaseCommit):'
353 352 def get_nodes(self, path):
354 353 if self._get_kind(path) != NodeKind.DIR:
355 354 raise CommitError(
356 "Directory does not exist for commit %s at "
357 " '%s'" % (self.raw_id, path))
355 "Directory does not exist for commit %s at '%s'" % (self.raw_id, path))
358 356 path = self._fix_path(path)
359 357 id_, _ = self._get_id_for_path(path)
360 358 tree_id = self._remote[id_]['id']
@@ -29,8 +29,7 b' from rhodecode.lib.vcs.backends import b'
29 29
30 30 class GitInMemoryCommit(base.BaseInMemoryCommit):
31 31
32 def commit(self, message, author, parents=None, branch=None, date=None,
33 **kwargs):
32 def commit(self, message, author, parents=None, branch=None, date=None, **kwargs):
34 33 """
35 34 Performs in-memory commit (doesn't check workdir in any way) and
36 35 returns newly created `GitCommit`. Updates repository's
@@ -94,12 +93,12 b' class GitInMemoryCommit(base.BaseInMemor'
94 93 commit_data, branch, commit_tree, updated, removed)
95 94
96 95 # Update vcs repository object
97 self.repository.commit_ids.append(commit_id)
98 self.repository._rebuild_cache(self.repository.commit_ids)
96 self.repository.append_commit_id(commit_id)
99 97
100 98 # invalidate parsed refs after commit
101 99 self.repository._refs = self.repository._get_refs()
102 100 self.repository.branches = self.repository._get_branches()
103 tip = self.repository.get_commit()
101 tip = self.repository.get_commit(commit_id)
102
104 103 self.reset()
105 104 return tip
@@ -25,8 +25,10 b' GIT repository module'
25 25 import logging
26 26 import os
27 27 import re
28 import time
28 29
29 30 from zope.cachedescriptors.property import Lazy as LazyProperty
31 from zope.cachedescriptors.property import CachedProperty
30 32
31 33 from rhodecode.lib.compat import OrderedDict
32 34 from rhodecode.lib.datelib import (
@@ -69,6 +71,9 b' class GitRepository(BaseRepository):'
69 71 # caches
70 72 self._commit_ids = {}
71 73
74 # dependent that trigger re-computation of commit_ids
75 self._commit_ids_ver = 0
76
72 77 @LazyProperty
73 78 def _remote(self):
74 79 return connection.Git(self.path, self.config, with_wire=self.with_wire)
@@ -81,7 +86,7 b' class GitRepository(BaseRepository):'
81 86 def head(self):
82 87 return self._remote.head()
83 88
84 @LazyProperty
89 @CachedProperty('_commit_ids_ver')
85 90 def commit_ids(self):
86 91 """
87 92 Returns list of commit ids, in ascending order. Being lazy
@@ -222,13 +227,10 b' class GitRepository(BaseRepository):'
222 227 return []
223 228 return output.splitlines()
224 229
225 def _get_commit_id(self, commit_id_or_idx):
230 def _lookup_commit(self, commit_id_or_idx, translate_tag=True):
226 231 def is_null(value):
227 232 return len(value) == commit_id_or_idx.count('0')
228 233
229 if self.is_empty():
230 raise EmptyRepositoryError("There are no commits yet")
231
232 234 if commit_id_or_idx in (None, '', 'tip', 'HEAD', 'head', -1):
233 235 return self.commit_ids[-1]
234 236
@@ -238,8 +240,7 b' class GitRepository(BaseRepository):'
238 240 try:
239 241 commit_id_or_idx = self.commit_ids[int(commit_id_or_idx)]
240 242 except Exception:
241 msg = "Commit %s does not exist for %s" % (
242 commit_id_or_idx, self)
243 msg = "Commit {} does not exist for `{}`".format(commit_id_or_idx, self.name)
243 244 raise CommitDoesNotExistError(msg)
244 245
245 246 elif is_bstr:
@@ -261,8 +262,7 b' class GitRepository(BaseRepository):'
261 262
262 263 if (not SHA_PATTERN.match(commit_id_or_idx) or
263 264 commit_id_or_idx not in self.commit_ids):
264 msg = "Commit %s does not exist for %s" % (
265 commit_id_or_idx, self)
265 msg = "Commit {} does not exist for `{}`".format(commit_id_or_idx, self.name)
266 266 raise CommitDoesNotExistError(msg)
267 267
268 268 # Ensure we return full id
@@ -431,19 +431,42 b' class GitRepository(BaseRepository):'
431 431 Returns `GitCommit` object representing commit from git repository
432 432 at the given `commit_id` or head (most recent commit) if None given.
433 433 """
434 if self.is_empty():
435 raise EmptyRepositoryError("There are no commits yet")
436
434 437 if commit_id is not None:
435 438 self._validate_commit_id(commit_id)
439 try:
440 # we have cached idx, use it without contacting the remote
441 idx = self._commit_ids[commit_id]
442 return GitCommit(self, commit_id, idx, pre_load=pre_load)
443 except KeyError:
444 pass
445
436 446 elif commit_idx is not None:
437 447 self._validate_commit_idx(commit_idx)
438 commit_id = commit_idx
439 commit_id = self._get_commit_id(commit_id)
448 try:
449 _commit_id = self.commit_ids[commit_idx]
450 if commit_idx < 0:
451 commit_idx = self.commit_ids.index(_commit_id)
452 return GitCommit(self, _commit_id, commit_idx, pre_load=pre_load)
453 except IndexError:
454 commit_id = commit_idx
455 else:
456 commit_id = "tip"
457
458 commit_id = self._lookup_commit(commit_id)
459 remote_idx = None
460 if translate_tag:
461 # Need to call remote to translate id for tagging scenario
462 remote_data = self._remote.get_object(commit_id)
463 commit_id = remote_data["commit_id"]
464 remote_idx = remote_data["idx"]
465
440 466 try:
441 if translate_tag:
442 # Need to call remote to translate id for tagging scenario
443 commit_id = self._remote.get_object(commit_id)["commit_id"]
444 467 idx = self._commit_ids[commit_id]
445 468 except KeyError:
446 raise RepositoryError("Cannot get object with id %s" % commit_id)
469 idx = remote_idx or 0
447 470
448 471 return GitCommit(self, commit_id, idx, pre_load=pre_load)
449 472
@@ -472,6 +495,7 b' class GitRepository(BaseRepository):'
472 495 """
473 496 if self.is_empty():
474 497 raise EmptyRepositoryError("There are no commits yet")
498
475 499 self._validate_branch_name(branch_name)
476 500
477 501 if start_id is not None:
@@ -479,9 +503,9 b' class GitRepository(BaseRepository):'
479 503 if end_id is not None:
480 504 self._validate_commit_id(end_id)
481 505
482 start_raw_id = self._get_commit_id(start_id)
506 start_raw_id = self._lookup_commit(start_id)
483 507 start_pos = self._commit_ids[start_raw_id] if start_id else None
484 end_raw_id = self._get_commit_id(end_id)
508 end_raw_id = self._lookup_commit(end_id)
485 509 end_pos = max(0, self._commit_ids[end_raw_id]) if end_id else None
486 510
487 511 if None not in [start_id, end_id] and start_pos > end_pos:
@@ -589,8 +613,9 b' class GitRepository(BaseRepository):'
589 613 commit = commit.parents[0]
590 614 self._remote.set_refs('refs/heads/%s' % branch_name, commit.raw_id)
591 615
592 self.commit_ids = self._get_all_commit_ids()
593 self._rebuild_cache(self.commit_ids)
616 self._commit_ids_ver = time.time()
617 # we updated _commit_ids_ver so accessing self.commit_ids will re-compute it
618 return len(self.commit_ids)
594 619
595 620 def get_common_ancestor(self, commit_id1, commit_id2, repo2):
596 621 if commit_id1 == commit_id2:
@@ -193,13 +193,6 b' class MercurialCommit(base.BaseCommit):'
193 193 children = self._remote.ctx_children(self.idx)
194 194 return self._make_commits(children)
195 195
196 def diff(self, ignore_whitespace=True, context=3):
197 result = self._remote.ctx_diff(
198 self.idx,
199 git=True, ignore_whitespace=ignore_whitespace, context=context)
200 diff = ''.join(result)
201 return MercurialDiff(diff)
202
203 196 def _fix_path(self, path):
204 197 """
205 198 Mercurial keeps filenodes as str so we need to encode from unicode
@@ -30,8 +30,7 b' from rhodecode.lib.vcs.exceptions import'
30 30
31 31 class MercurialInMemoryCommit(BaseInMemoryCommit):
32 32
33 def commit(self, message, author, parents=None, branch=None, date=None,
34 **kwargs):
33 def commit(self, message, author, parents=None, branch=None, date=None, **kwargs):
35 34 """
36 35 Performs in-memory commit (doesn't check workdir in any way) and
37 36 returns newly created `MercurialCommit`. Updates repository's
@@ -83,15 +82,14 b' class MercurialInMemoryCommit(BaseInMemo'
83 82
84 83 date, tz = date_to_timestamp_plus_offset(date)
85 84
86 new_id = self.repository._remote.commitctx(
85 commit_id = self.repository._remote.commitctx(
87 86 message=message, parents=parent_ids,
88 87 commit_time=date, commit_timezone=tz, user=author,
89 88 files=self.get_paths(), extra=kwargs, removed=removed,
90 89 updated=updated)
90 self.repository.append_commit_id(commit_id)
91 91
92 self.repository.commit_ids.append(new_id)
93 self.repository._rebuild_cache(self.repository.commit_ids)
94 92 self.repository.branches = self.repository._get_branches()
95 tip = self.repository.get_commit()
93 tip = self.repository.get_commit(commit_id)
96 94 self.reset()
97 95 return tip
@@ -24,9 +24,11 b' HG repository module'
24 24 import os
25 25 import logging
26 26 import binascii
27 import time
27 28 import urllib
28 29
29 30 from zope.cachedescriptors.property import Lazy as LazyProperty
31 from zope.cachedescriptors.property import CachedProperty
30 32
31 33 from rhodecode.lib.compat import OrderedDict
32 34 from rhodecode.lib.datelib import (
@@ -85,11 +87,14 b' class MercurialRepository(BaseRepository'
85 87 # caches
86 88 self._commit_ids = {}
87 89
90 # dependent that trigger re-computation of commit_ids
91 self._commit_ids_ver = 0
92
88 93 @LazyProperty
89 94 def _remote(self):
90 95 return connection.Hg(self.path, self.config, with_wire=self.with_wire)
91 96
92 @LazyProperty
97 @CachedProperty('_commit_ids_ver')
93 98 def commit_ids(self):
94 99 """
95 100 Returns list of commit ids, in ascending order. Being lazy
@@ -157,8 +162,7 b' class MercurialRepository(BaseRepository'
157 162
158 163 return OrderedDict(sorted(_tags, key=get_name, reverse=True))
159 164
160 def tag(self, name, user, commit_id=None, message=None, date=None,
161 **kwargs):
165 def tag(self, name, user, commit_id=None, message=None, date=None, **kwargs):
162 166 """
163 167 Creates and returns a tag for the given ``commit_id``.
164 168
@@ -172,6 +176,7 b' class MercurialRepository(BaseRepository'
172 176 """
173 177 if name in self.tags:
174 178 raise TagAlreadyExistError("Tag %s already exists" % name)
179
175 180 commit = self.get_commit(commit_id=commit_id)
176 181 local = kwargs.setdefault('local', False)
177 182
@@ -180,8 +185,7 b' class MercurialRepository(BaseRepository'
180 185
181 186 date, tz = date_to_timestamp_plus_offset(date)
182 187
183 self._remote.tag(
184 name, commit.raw_id, message, local, user, date, tz)
188 self._remote.tag(name, commit.raw_id, message, local, user, date, tz)
185 189 self._remote.invalidate_vcs_cache()
186 190
187 191 # Reinitialize tags
@@ -203,6 +207,7 b' class MercurialRepository(BaseRepository'
203 207 """
204 208 if name not in self.tags:
205 209 raise TagDoesNotExistError("Tag %s does not exist" % name)
210
206 211 if message is None:
207 212 message = "Removed tag %s" % name
208 213 local = False
@@ -271,8 +276,9 b' class MercurialRepository(BaseRepository'
271 276 self._remote.strip(commit_id, update=False, backup="none")
272 277
273 278 self._remote.invalidate_vcs_cache()
274 self.commit_ids = self._get_all_commit_ids()
275 self._rebuild_cache(self.commit_ids)
279 self._commit_ids_ver = time.time()
280 # we updated _commit_ids_ver so accessing self.commit_ids will re-compute it
281 return len(self.commit_ids)
276 282
277 283 def verify(self):
278 284 verify = self._remote.verify()
@@ -425,18 +431,20 b' class MercurialRepository(BaseRepository'
425 431 if commit_id is not None:
426 432 self._validate_commit_id(commit_id)
427 433 try:
434 # we have cached idx, use it without contacting the remote
428 435 idx = self._commit_ids[commit_id]
429 436 return MercurialCommit(self, commit_id, idx, pre_load=pre_load)
430 437 except KeyError:
431 438 pass
439
432 440 elif commit_idx is not None:
433 441 self._validate_commit_idx(commit_idx)
434 442 try:
435 id_ = self.commit_ids[commit_idx]
443 _commit_id = self.commit_ids[commit_idx]
436 444 if commit_idx < 0:
437 commit_idx += len(self.commit_ids)
438 return MercurialCommit(
439 self, id_, commit_idx, pre_load=pre_load)
445 commit_idx = self.commit_ids.index(_commit_id)
446
447 return MercurialCommit(self, _commit_id, commit_idx, pre_load=pre_load)
440 448 except IndexError:
441 449 commit_id = commit_idx
442 450 else:
@@ -448,8 +456,8 b' class MercurialRepository(BaseRepository'
448 456 try:
449 457 raw_id, idx = self._remote.lookup(commit_id, both=True)
450 458 except CommitDoesNotExistError:
451 msg = "Commit %s does not exist for %s" % (
452 commit_id, self)
459 msg = "Commit {} does not exist for `{}`".format(
460 *map(safe_str, [commit_id, self.name]))
453 461 raise CommitDoesNotExistError(msg)
454 462
455 463 return MercurialCommit(self, raw_id, idx, pre_load=pre_load)
@@ -477,11 +485,11 b' class MercurialRepository(BaseRepository'
477 485 ``end`` could not be found.
478 486 """
479 487 # actually we should check now if it's not an empty repo
480 branch_ancestors = False
481 488 if self.is_empty():
482 489 raise EmptyRepositoryError("There are no commits yet")
483 490 self._validate_branch_name(branch_name)
484 491
492 branch_ancestors = False
485 493 if start_id is not None:
486 494 self._validate_commit_id(start_id)
487 495 c_start = self.get_commit(commit_id=start_id)
@@ -715,11 +723,16 b' class MercurialRepository(BaseRepository'
715 723
716 724 try:
717 725 if target_ref.type == 'branch' and len(self._heads(target_ref.name)) != 1:
718 heads = ','.join(self._heads(target_ref.name))
726 heads = '\n,'.join(self._heads(target_ref.name))
727 metadata = {
728 'target_ref': target_ref,
729 'source_ref': source_ref,
730 'heads': heads
731 }
719 732 return MergeResponse(
720 733 False, False, None,
721 734 MergeFailureReason.HG_TARGET_HAS_MULTIPLE_HEADS,
722 metadata={'heads': heads})
735 metadata=metadata)
723 736 except CommitDoesNotExistError:
724 737 log.exception('Failure when looking up branch heads on hg target')
725 738 return MergeResponse(
@@ -892,11 +905,15 b' class MercurialRepository(BaseRepository'
892 905
893 906 def read_patterns(suffix):
894 907 svalue = None
895 try:
896 svalue = hgacl.get('narrowhgacl', username + suffix)
897 except configparser.NoOptionError:
908 for section, option in [
909 ('narrowacl', username + suffix),
910 ('narrowacl', 'default' + suffix),
911 ('narrowhgacl', username + suffix),
912 ('narrowhgacl', 'default' + suffix)
913 ]:
898 914 try:
899 svalue = hgacl.get('narrowhgacl', 'default' + suffix)
915 svalue = hgacl.get(section, option)
916 break # stop at the first value we find
900 917 except configparser.NoOptionError:
901 918 pass
902 919 if not svalue:
@@ -30,8 +30,7 b' from rhodecode.lib.vcs.backends import b'
30 30
31 31 class SubversionInMemoryCommit(base.BaseInMemoryCommit):
32 32
33 def commit(self, message, author, parents=None, branch=None, date=None,
34 **kwargs):
33 def commit(self, message, author, parents=None, branch=None, date=None, **kwargs):
35 34 if branch not in (None, self.repository.DEFAULT_BRANCH_NAME):
36 35 raise NotImplementedError("Branches are not yet supported")
37 36
@@ -74,8 +73,7 b' class SubversionInMemoryCommit(base.Base'
74 73 # we should not add the commit_id, if it is already evaluated, it
75 74 # will not be evaluated again.
76 75 commit_id = str(svn_rev)
77 if commit_id not in self.repository.commit_ids:
78 self.repository.commit_ids.append(commit_id)
76 self.repository.append_commit_id(commit_id)
79 77 tip = self.repository.get_commit()
80 78 self.reset()
81 79 return tip
@@ -27,6 +27,7 b' import os'
27 27 import urllib
28 28
29 29 from zope.cachedescriptors.property import Lazy as LazyProperty
30 from zope.cachedescriptors.property import CachedProperty
30 31
31 32 from rhodecode.lib.compat import OrderedDict
32 33 from rhodecode.lib.datelib import date_astimestamp
@@ -75,6 +76,9 b' class SubversionRepository(base.BaseRepo'
75 76
76 77 self._init_repo(create, src_url)
77 78
79 # dependent that trigger re-computation of commit_ids
80 self._commit_ids_ver = 0
81
78 82 @LazyProperty
79 83 def _remote(self):
80 84 return connection.Svn(self.path, self.config)
@@ -93,11 +97,31 b' class SubversionRepository(base.BaseRepo'
93 97 else:
94 98 self._check_path()
95 99
96 @LazyProperty
100 @CachedProperty('_commit_ids_ver')
97 101 def commit_ids(self):
98 102 head = self._remote.lookup(None)
99 103 return [str(r) for r in xrange(1, head + 1)]
100 104
105 def _rebuild_cache(self, commit_ids):
106 pass
107
108 def run_svn_command(self, cmd, **opts):
109 """
110 Runs given ``cmd`` as svn command and returns tuple
111 (stdout, stderr).
112
113 :param cmd: full svn command to be executed
114 :param opts: env options to pass into Subprocess command
115 """
116 if not isinstance(cmd, list):
117 raise ValueError('cmd must be a list, got %s instead' % type(cmd))
118
119 skip_stderr_log = opts.pop('skip_stderr_log', False)
120 out, err = self._remote.run_svn_command(cmd, **opts)
121 if err and not skip_stderr_log:
122 log.debug('Stderr output of svn command "%s":\n%s', cmd, err)
123 return out, err
124
101 125 @LazyProperty
102 126 def branches(self):
103 127 return self._tags_or_branches('vcs_svn_branch')
@@ -260,7 +284,7 b' class SubversionRepository(base.BaseRepo'
260 284 try:
261 285 commit_id = self.commit_ids[commit_idx]
262 286 except IndexError:
263 raise CommitDoesNotExistError
287 raise CommitDoesNotExistError('No commit with idx: {}'.format(commit_idx))
264 288
265 289 commit_id = self._sanitize_commit_id(commit_id)
266 290 commit = SubversionCommit(repository=self, commit_id=commit_id)
@@ -42,12 +42,16 b' BACKENDS = {'
42 42 'svn': 'rhodecode.lib.vcs.backends.svn.SubversionRepository',
43 43 }
44 44
45 # TODO: Remove once controllers/files.py is adjusted
46 ARCHIVE_SPECS = {
47 'tbz2': ('application/x-bzip2', '.tar.bz2'),
48 'tgz': ('application/x-gzip', '.tar.gz'),
49 'zip': ('application/zip', '.zip'),
50 }
45
46 ARCHIVE_SPECS = [
47 ('tbz2', 'application/x-bzip2', 'tbz2'),
48 ('tbz2', 'application/x-bzip2', '.tar.bz2'),
49
50 ('tgz', 'application/x-gzip', '.tgz'),
51 ('tgz', 'application/x-gzip', '.tar.gz'),
52
53 ('zip', 'application/zip', '.zip'),
54 ]
51 55
52 56 HOOKS_PROTOCOL = None
53 57 HOOKS_DIRECT_CALLS = False
@@ -101,23 +101,35 b' def parse_datetime(text):'
101 101 :param text: string of desired date/datetime or something more verbose,
102 102 like *yesterday*, *2weeks 3days*, etc.
103 103 """
104 if not text:
105 raise ValueError('Wrong date: "%s"' % text)
104 106
105 text = text.strip().lower()
107 if isinstance(text, datetime.datetime):
108 return text
106 109
107 INPUT_FORMATS = (
110 # we limit a format to no include microseconds e.g 2017-10-17t17:48:23.XXXX
111 text = text.strip().lower()[:19]
112
113 input_formats = (
108 114 '%Y-%m-%d %H:%M:%S',
115 '%Y-%m-%dt%H:%M:%S',
109 116 '%Y-%m-%d %H:%M',
117 '%Y-%m-%dt%H:%M',
110 118 '%Y-%m-%d',
111 119 '%m/%d/%Y %H:%M:%S',
120 '%m/%d/%Yt%H:%M:%S',
112 121 '%m/%d/%Y %H:%M',
122 '%m/%d/%Yt%H:%M',
113 123 '%m/%d/%Y',
114 124 '%m/%d/%y %H:%M:%S',
125 '%m/%d/%yt%H:%M:%S',
115 126 '%m/%d/%y %H:%M',
127 '%m/%d/%yt%H:%M',
116 128 '%m/%d/%y',
117 129 )
118 for format in INPUT_FORMATS:
130 for format_def in input_formats:
119 131 try:
120 return datetime.datetime(*time.strptime(text, format)[:6])
132 return datetime.datetime(*time.strptime(text, format_def)[:6])
121 133 except ValueError:
122 134 pass
123 135
@@ -25,6 +25,7 b' Database Models for RhodeCode Enterprise'
25 25 import re
26 26 import os
27 27 import time
28 import string
28 29 import hashlib
29 30 import logging
30 31 import datetime
@@ -39,7 +40,7 b' from sqlalchemy import ('
39 40 Index, Sequence, UniqueConstraint, ForeignKey, CheckConstraint, Column,
40 41 Boolean, String, Unicode, UnicodeText, DateTime, Integer, LargeBinary,
41 42 Text, Float, PickleType)
42 from sqlalchemy.sql.expression import true, false
43 from sqlalchemy.sql.expression import true, false, case
43 44 from sqlalchemy.sql.functions import coalesce, count # pragma: no cover
44 45 from sqlalchemy.orm import (
45 46 relationship, joinedload, class_mapper, validates, aliased)
@@ -50,6 +51,7 b' from sqlalchemy.dialects.mysql import LO'
50 51 from zope.cachedescriptors.property import Lazy as LazyProperty
51 52 from pyramid import compat
52 53 from pyramid.threadlocal import get_current_request
54 from webhelpers.text import collapse, remove_formatting
53 55
54 56 from rhodecode.translation import _
55 57 from rhodecode.lib.vcs import get_vcs_instance
@@ -57,13 +59,13 b' from rhodecode.lib.vcs.backends.base imp'
57 59 from rhodecode.lib.utils2 import (
58 60 str2bool, safe_str, get_commit_safe, safe_unicode, sha1_safe,
59 61 time_to_datetime, aslist, Optional, safe_int, get_clone_url, AttributeDict,
60 glob2re, StrictAttributeDict, cleaned_uri)
62 glob2re, StrictAttributeDict, cleaned_uri, datetime_to_time, OrderedDefaultDict)
61 63 from rhodecode.lib.jsonalchemy import MutationObj, MutationList, JsonType, \
62 64 JsonRaw
63 65 from rhodecode.lib.ext_json import json
64 66 from rhodecode.lib.caching_query import FromCache
65 from rhodecode.lib.encrypt import AESCipher
66
67 from rhodecode.lib.encrypt import AESCipher, validate_and_get_enc_data
68 from rhodecode.lib.encrypt2 import Encryptor
67 69 from rhodecode.model.meta import Base, Session
68 70
69 71 URL_SEP = '/'
@@ -159,44 +161,46 b' class EncryptedTextValue(TypeDecorator):'
159 161 impl = Text
160 162
161 163 def process_bind_param(self, value, dialect):
162 if not value:
163 return value
164 if value.startswith('enc$aes$') or value.startswith('enc$aes_hmac$'):
165 # protect against double encrypting if someone manually starts
166 # doing
167 raise ValueError('value needs to be in unencrypted format, ie. '
168 'not starting with enc$aes')
169 return 'enc$aes_hmac$%s' % AESCipher(
170 ENCRYPTION_KEY, hmac=True).encrypt(value)
171
172 def process_result_value(self, value, dialect):
164 """
165 Setter for storing value
166 """
173 167 import rhodecode
174
175 168 if not value:
176 169 return value
177 170
178 parts = value.split('$', 3)
179 if not len(parts) == 3:
180 # probably not encrypted values
181 return value
171 # protect against double encrypting if values is already encrypted
172 if value.startswith('enc$aes$') \
173 or value.startswith('enc$aes_hmac$') \
174 or value.startswith('enc2$'):
175 raise ValueError('value needs to be in unencrypted format, '
176 'ie. not starting with enc$ or enc2$')
177
178 algo = rhodecode.CONFIG.get('rhodecode.encrypted_values.algorithm') or 'aes'
179 if algo == 'aes':
180 return 'enc$aes_hmac$%s' % AESCipher(ENCRYPTION_KEY, hmac=True).encrypt(value)
181 elif algo == 'fernet':
182 return Encryptor(ENCRYPTION_KEY).encrypt(value)
182 183 else:
183 if parts[0] != 'enc':
184 # parts ok but without our header ?
185 return value
186 enc_strict_mode = str2bool(rhodecode.CONFIG.get(
187 'rhodecode.encrypted_values.strict') or True)
188 # at that stage we know it's our encryption
189 if parts[1] == 'aes':
190 decrypted_data = AESCipher(ENCRYPTION_KEY).decrypt(parts[2])
191 elif parts[1] == 'aes_hmac':
192 decrypted_data = AESCipher(
193 ENCRYPTION_KEY, hmac=True,
194 strict_verification=enc_strict_mode).decrypt(parts[2])
195 else:
196 raise ValueError(
197 'Encryption type part is wrong, must be `aes` '
198 'or `aes_hmac`, got `%s` instead' % (parts[1]))
199 return decrypted_data
184 ValueError('Bad encryption algorithm, should be fernet or aes, got: {}'.format(algo))
185
186 def process_result_value(self, value, dialect):
187 """
188 Getter for retrieving value
189 """
190
191 import rhodecode
192 if not value:
193 return value
194
195 algo = rhodecode.CONFIG.get('rhodecode.encrypted_values.algorithm') or 'aes'
196 enc_strict_mode = str2bool(rhodecode.CONFIG.get('rhodecode.encrypted_values.strict') or True)
197 if algo == 'aes':
198 decrypted_data = validate_and_get_enc_data(value, ENCRYPTION_KEY, enc_strict_mode)
199 elif algo == 'fernet':
200 return Encryptor(ENCRYPTION_KEY).decrypt(value)
201 else:
202 ValueError('Bad encryption algorithm, should be fernet or aes, got: {}'.format(algo))
203 return decrypted_data
200 204
201 205
202 206 class BaseModel(object):
@@ -407,6 +411,15 b' class RhodeCodeUi(Base, BaseModel):'
407 411 HOOK_PUSH = 'changegroup.push_logger'
408 412 HOOK_PUSH_KEY = 'pushkey.key_push'
409 413
414 HOOKS_BUILTIN = [
415 HOOK_PRE_PULL,
416 HOOK_PULL,
417 HOOK_PRE_PUSH,
418 HOOK_PRETX_PUSH,
419 HOOK_PUSH,
420 HOOK_PUSH_KEY,
421 ]
422
410 423 # TODO: johbo: Unify way how hooks are configured for git and hg,
411 424 # git part is currently hardcoded.
412 425
@@ -1665,11 +1678,12 b' class Repository(Base, BaseModel):'
1665 1678 cascade="all, delete, delete-orphan")
1666 1679 ui = relationship('RepoRhodeCodeUi', cascade="all")
1667 1680 settings = relationship('RepoRhodeCodeSetting', cascade="all")
1668 integrations = relationship('Integration',
1669 cascade="all, delete, delete-orphan")
1681 integrations = relationship('Integration', cascade="all, delete, delete-orphan")
1670 1682
1671 1683 scoped_tokens = relationship('UserApiKeys', cascade="all")
1672 1684
1685 artifacts = relationship('FileStore', cascade="all")
1686
1673 1687 def __unicode__(self):
1674 1688 return u"<%s('%s:%s')>" % (self.__class__.__name__, self.repo_id,
1675 1689 safe_unicode(self.repo_name))
@@ -1717,7 +1731,9 b' class Repository(Base, BaseModel):'
1717 1731 from rhodecode.lib.vcs.backends.base import EmptyCommit
1718 1732 dummy = EmptyCommit().__json__()
1719 1733 if not self._changeset_cache:
1720 return dummy
1734 dummy['source_repo_id'] = self.repo_id
1735 return json.loads(json.dumps(dummy))
1736
1721 1737 try:
1722 1738 return json.loads(self._changeset_cache)
1723 1739 except TypeError:
@@ -2170,6 +2186,20 b' class Repository(Base, BaseModel):'
2170 2186 return make_lock, currently_locked, lock_info
2171 2187
2172 2188 @property
2189 def last_commit_cache_update_diff(self):
2190 return time.time() - (safe_int(self.changeset_cache.get('updated_on')) or 0)
2191
2192 @property
2193 def last_commit_change(self):
2194 from rhodecode.lib.vcs.utils.helpers import parse_datetime
2195 empty_date = datetime.datetime.fromtimestamp(0)
2196 date_latest = self.changeset_cache.get('date', empty_date)
2197 try:
2198 return parse_datetime(date_latest)
2199 except Exception:
2200 return empty_date
2201
2202 @property
2173 2203 def last_db_change(self):
2174 2204 return self.updated_on
2175 2205
@@ -2262,6 +2292,7 b' class Repository(Base, BaseModel):'
2262 2292 """
2263 2293 Update cache of last changeset for repository, keys should be::
2264 2294
2295 source_repo_id
2265 2296 short_id
2266 2297 raw_id
2267 2298 revision
@@ -2269,15 +2300,15 b' class Repository(Base, BaseModel):'
2269 2300 message
2270 2301 date
2271 2302 author
2272
2273 :param cs_cache:
2303 updated_on
2304
2274 2305 """
2275 2306 from rhodecode.lib.vcs.backends.base import BaseChangeset
2276 2307 if cs_cache is None:
2277 2308 # use no-cache version here
2278 2309 scm_repo = self.scm_instance(cache=False, config=config)
2279 2310
2280 empty = not scm_repo or scm_repo.is_empty()
2311 empty = scm_repo is None or scm_repo.is_empty()
2281 2312 if not empty:
2282 2313 cs_cache = scm_repo.get_commit(
2283 2314 pre_load=["author", "date", "message", "parents"])
@@ -2297,18 +2328,28 b' class Repository(Base, BaseModel):'
2297 2328 if is_outdated(cs_cache) or not self.changeset_cache:
2298 2329 _default = datetime.datetime.utcnow()
2299 2330 last_change = cs_cache.get('date') or _default
2300 if self.updated_on and self.updated_on > last_change:
2301 # we check if last update is newer than the new value
2302 # if yes, we use the current timestamp instead. Imagine you get
2303 # old commit pushed 1y ago, we'd set last update 1y to ago.
2304 last_change = _default
2305 log.debug('updated repo %s with new cs cache %s',
2306 self.repo_name, cs_cache)
2307 self.updated_on = last_change
2331 # we check if last update is newer than the new value
2332 # if yes, we use the current timestamp instead. Imagine you get
2333 # old commit pushed 1y ago, we'd set last update 1y to ago.
2334 last_change_timestamp = datetime_to_time(last_change)
2335 current_timestamp = datetime_to_time(last_change)
2336 if last_change_timestamp > current_timestamp:
2337 cs_cache['date'] = _default
2338
2339 cs_cache['updated_on'] = time.time()
2308 2340 self.changeset_cache = cs_cache
2309 2341 Session().add(self)
2310 2342 Session().commit()
2343
2344 log.debug('updated repo %s with new commit cache %s',
2345 self.repo_name, cs_cache)
2311 2346 else:
2347 cs_cache = self.changeset_cache
2348 cs_cache['updated_on'] = time.time()
2349 self.changeset_cache = cs_cache
2350 Session().add(self)
2351 Session().commit()
2352
2312 2353 log.debug('Skipping update_commit_cache for repo:`%s` '
2313 2354 'commit already with latest changes', self.repo_name)
2314 2355
@@ -2397,6 +2438,7 b' class Repository(Base, BaseModel):'
2397 2438 # control over cache behaviour
2398 2439 if cache is None and full_cache and not config:
2399 2440 return self._get_instance_cached()
2441 # cache here is sent to the "vcs server"
2400 2442 return self._get_instance(cache=bool(cache), config=config)
2401 2443
2402 2444 def _get_instance_cached(self):
@@ -2425,8 +2467,7 b' class Repository(Base, BaseModel):'
2425 2467 else:
2426 2468 instance = get_instance_cached(*args)
2427 2469
2428 log.debug(
2429 'Repo instance fetched in %.3fs', inv_context_manager.compute_time)
2470 log.debug('Repo instance fetched in %.3fs', inv_context_manager.compute_time)
2430 2471 return instance
2431 2472
2432 2473 def _get_instance(self, cache=True, config=None):
@@ -2440,7 +2481,8 b' class Repository(Base, BaseModel):'
2440 2481 with_wire=custom_wire,
2441 2482 create=False,
2442 2483 _vcs_alias=self.repo_type)
2443
2484 if repo is not None:
2485 repo.count() # cache rebuild
2444 2486 return repo
2445 2487
2446 2488 def __json__(self):
@@ -2467,7 +2509,8 b' class RepoGroup(Base, BaseModel):'
2467 2509 CHOICES_SEPARATOR = '/' # used to generate select2 choices for nested groups
2468 2510
2469 2511 group_id = Column("group_id", Integer(), nullable=False, unique=True, default=None, primary_key=True)
2470 group_name = Column("group_name", String(255), nullable=False, unique=True, default=None)
2512 _group_name = Column("group_name", String(255), nullable=False, unique=True, default=None)
2513 group_name_hash = Column("repo_group_name_hash", String(1024), nullable=False, unique=False)
2471 2514 group_parent_id = Column("group_parent_id", Integer(), ForeignKey('groups.group_id'), nullable=True, unique=None, default=None)
2472 2515 group_description = Column("group_description", String(10000), nullable=True, unique=None, default=None)
2473 2516 enable_locking = Column("enable_locking", Boolean(), nullable=False, unique=None, default=False)
@@ -2475,6 +2518,8 b' class RepoGroup(Base, BaseModel):'
2475 2518 created_on = Column('created_on', DateTime(timezone=False), nullable=False, default=datetime.datetime.now)
2476 2519 updated_on = Column('updated_on', DateTime(timezone=False), nullable=True, unique=None, default=datetime.datetime.now)
2477 2520 personal = Column('personal', Boolean(), nullable=True, unique=None, default=None)
2521 _changeset_cache = Column(
2522 "changeset_cache", LargeBinary(), nullable=True) # JSON data
2478 2523
2479 2524 repo_group_to_perm = relationship('UserRepoGroupToPerm', cascade='all', order_by='UserRepoGroupToPerm.group_to_perm_id')
2480 2525 users_group_to_perm = relationship('UserGroupRepoGroupToPerm', cascade='all')
@@ -2490,6 +2535,38 b' class RepoGroup(Base, BaseModel):'
2490 2535 return u"<%s('id:%s:%s')>" % (
2491 2536 self.__class__.__name__, self.group_id, self.group_name)
2492 2537
2538 @hybrid_property
2539 def group_name(self):
2540 return self._group_name
2541
2542 @group_name.setter
2543 def group_name(self, value):
2544 self._group_name = value
2545 self.group_name_hash = self.hash_repo_group_name(value)
2546
2547 @hybrid_property
2548 def changeset_cache(self):
2549 from rhodecode.lib.vcs.backends.base import EmptyCommit
2550 dummy = EmptyCommit().__json__()
2551 if not self._changeset_cache:
2552 dummy['source_repo_id'] = ''
2553 return json.loads(json.dumps(dummy))
2554
2555 try:
2556 return json.loads(self._changeset_cache)
2557 except TypeError:
2558 return dummy
2559 except Exception:
2560 log.error(traceback.format_exc())
2561 return dummy
2562
2563 @changeset_cache.setter
2564 def changeset_cache(self, val):
2565 try:
2566 self._changeset_cache = json.dumps(val)
2567 except Exception:
2568 log.error(traceback.format_exc())
2569
2493 2570 @validates('group_parent_id')
2494 2571 def validate_group_parent_id(self, key, val):
2495 2572 """
@@ -2506,6 +2583,18 b' class RepoGroup(Base, BaseModel):'
2506 2583 return h.escape(self.group_description)
2507 2584
2508 2585 @classmethod
2586 def hash_repo_group_name(cls, repo_group_name):
2587 val = remove_formatting(repo_group_name)
2588 val = safe_str(val).lower()
2589 chars = []
2590 for c in val:
2591 if c not in string.ascii_letters:
2592 c = str(ord(c))
2593 chars.append(c)
2594
2595 return ''.join(chars)
2596
2597 @classmethod
2509 2598 def _generate_choice(cls, repo_group):
2510 2599 from webhelpers.html import literal as _literal
2511 2600 _name = lambda k: _literal(cls.CHOICES_SEPARATOR.join(k))
@@ -2573,8 +2662,7 b' class RepoGroup(Base, BaseModel):'
2573 2662 return q.all()
2574 2663
2575 2664 @property
2576 def parents(self):
2577 parents_recursion_limit = 10
2665 def parents(self, parents_recursion_limit = 10):
2578 2666 groups = []
2579 2667 if self.parent_group is None:
2580 2668 return groups
@@ -2597,6 +2685,20 b' class RepoGroup(Base, BaseModel):'
2597 2685 return groups
2598 2686
2599 2687 @property
2688 def last_commit_cache_update_diff(self):
2689 return time.time() - (safe_int(self.changeset_cache.get('updated_on')) or 0)
2690
2691 @property
2692 def last_commit_change(self):
2693 from rhodecode.lib.vcs.utils.helpers import parse_datetime
2694 empty_date = datetime.datetime.fromtimestamp(0)
2695 date_latest = self.changeset_cache.get('date', empty_date)
2696 try:
2697 return parse_datetime(date_latest)
2698 except Exception:
2699 return empty_date
2700
2701 @property
2600 2702 def last_db_change(self):
2601 2703 return self.updated_on
2602 2704
@@ -2635,7 +2737,7 b' class RepoGroup(Base, BaseModel):'
2635 2737
2636 2738 return cnt + children_count(self)
2637 2739
2638 def _recursive_objects(self, include_repos=True):
2740 def _recursive_objects(self, include_repos=True, include_groups=True):
2639 2741 all_ = []
2640 2742
2641 2743 def _get_members(root_gr):
@@ -2645,11 +2747,16 b' class RepoGroup(Base, BaseModel):'
2645 2747 childs = root_gr.children.all()
2646 2748 if childs:
2647 2749 for gr in childs:
2648 all_.append(gr)
2750 if include_groups:
2751 all_.append(gr)
2649 2752 _get_members(gr)
2650 2753
2754 root_group = []
2755 if include_groups:
2756 root_group = [self]
2757
2651 2758 _get_members(self)
2652 return [self] + all_
2759 return root_group + all_
2653 2760
2654 2761 def recursive_groups_and_repos(self):
2655 2762 """
@@ -2663,6 +2770,12 b' class RepoGroup(Base, BaseModel):'
2663 2770 """
2664 2771 return self._recursive_objects(include_repos=False)
2665 2772
2773 def recursive_repos(self):
2774 """
2775 Returns all children repositories for this group
2776 """
2777 return self._recursive_objects(include_groups=False)
2778
2666 2779 def get_new_name(self, group_name):
2667 2780 """
2668 2781 returns new full group name based on parent and new name
@@ -2673,6 +2786,63 b' class RepoGroup(Base, BaseModel):'
2673 2786 self.parent_group else [])
2674 2787 return RepoGroup.url_sep().join(path_prefix + [group_name])
2675 2788
2789 def update_commit_cache(self, config=None):
2790 """
2791 Update cache of last changeset for newest repository inside this group, keys should be::
2792
2793 source_repo_id
2794 short_id
2795 raw_id
2796 revision
2797 parents
2798 message
2799 date
2800 author
2801
2802 """
2803 from rhodecode.lib.vcs.utils.helpers import parse_datetime
2804
2805 def repo_groups_and_repos():
2806 all_entries = OrderedDefaultDict(list)
2807
2808 def _get_members(root_gr, pos=0):
2809
2810 for repo in root_gr.repositories:
2811 all_entries[root_gr].append(repo)
2812
2813 # fill in all parent positions
2814 for parent_group in root_gr.parents:
2815 all_entries[parent_group].extend(all_entries[root_gr])
2816
2817 children_groups = root_gr.children.all()
2818 if children_groups:
2819 for cnt, gr in enumerate(children_groups, 1):
2820 _get_members(gr, pos=pos+cnt)
2821
2822 _get_members(root_gr=self)
2823 return all_entries
2824
2825 empty_date = datetime.datetime.fromtimestamp(0)
2826 for repo_group, repos in repo_groups_and_repos().items():
2827
2828 latest_repo_cs_cache = {}
2829 for repo in repos:
2830 repo_cs_cache = repo.changeset_cache
2831 date_latest = latest_repo_cs_cache.get('date', empty_date)
2832 date_current = repo_cs_cache.get('date', empty_date)
2833 current_timestamp = datetime_to_time(parse_datetime(date_latest))
2834 if current_timestamp < datetime_to_time(parse_datetime(date_current)):
2835 latest_repo_cs_cache = repo_cs_cache
2836 latest_repo_cs_cache['source_repo_id'] = repo.repo_id
2837
2838 latest_repo_cs_cache['updated_on'] = time.time()
2839 repo_group.changeset_cache = latest_repo_cs_cache
2840 Session().add(repo_group)
2841 Session().commit()
2842
2843 log.debug('updated repo group %s with new commit cache %s',
2844 repo_group.group_name, latest_repo_cs_cache)
2845
2676 2846 def permissions(self, with_admins=True, with_owner=True,
2677 2847 expand_from_user_groups=False):
2678 2848 """
@@ -2768,6 +2938,13 b' class RepoGroup(Base, BaseModel):'
2768 2938 }
2769 2939 return data
2770 2940
2941 def get_dict(self):
2942 # Since we transformed `group_name` to a hybrid property, we need to
2943 # keep compatibility with the code which uses `group_name` field.
2944 result = super(RepoGroup, self).get_dict()
2945 result['group_name'] = result.pop('_group_name', None)
2946 return result
2947
2771 2948
2772 2949 class Permission(Base, BaseModel):
2773 2950 __tablename__ = 'permissions'
@@ -4258,9 +4435,16 b' class Gist(Base, BaseModel):'
4258 4435 # SCM functions
4259 4436
4260 4437 def scm_instance(self, **kwargs):
4438 """
4439 Get an instance of VCS Repository
4440
4441 :param kwargs:
4442 """
4443 from rhodecode.model.gist import GistModel
4261 4444 full_repo_path = os.path.join(self.base_path(), self.gist_access_id)
4262 4445 return get_vcs_instance(
4263 repo_path=safe_str(full_repo_path), create=False)
4446 repo_path=safe_str(full_repo_path), create=False,
4447 _vcs_alias=GistModel.vcs_backend)
4264 4448
4265 4449
4266 4450 class ExternalIdentity(Base, BaseModel):
@@ -4904,8 +5088,8 b' class FileStore(Base, BaseModel):'
4904 5088
4905 5089 @classmethod
4906 5090 def create(cls, file_uid, filename, file_hash, file_size, file_display_name='',
4907 file_description='', enabled=True, check_acl=True,
4908 user_id=None, scope_repo_id=None, scope_repo_group_id=None):
5091 file_description='', enabled=True, check_acl=True, user_id=None,
5092 scope_user_id=None, scope_repo_id=None, scope_repo_group_id=None):
4909 5093
4910 5094 store_entry = FileStore()
4911 5095 store_entry.file_uid = file_uid
@@ -4919,6 +5103,7 b' class FileStore(Base, BaseModel):'
4919 5103 store_entry.enabled = enabled
4920 5104
4921 5105 store_entry.user_id = user_id
5106 store_entry.scope_user_id = scope_user_id
4922 5107 store_entry.scope_repo_id = scope_repo_id
4923 5108 store_entry.scope_repo_group_id = scope_repo_group_id
4924 5109 return store_entry
@@ -618,7 +618,7 b' def PullRequestForm(localizer, repo_id):'
618 618 revisions = All(#v.NotReviewedRevisions(localizer, repo_id)(),
619 619 v.UniqueList(localizer)(not_empty=True))
620 620 review_members = formencode.ForEach(ReviewerForm())
621 pullrequest_title = v.UnicodeString(strip=True, required=True, min=3, max=255)
621 pullrequest_title = v.UnicodeString(strip=True, required=True, min=1, max=255)
622 622 pullrequest_desc = v.UnicodeString(strip=True, required=False)
623 623 description_renderer = v.UnicodeString(strip=True, required=False)
624 624
@@ -47,6 +47,7 b" GIST_METADATA_FILE = '.rc_gist_metadata'"
47 47
48 48 class GistModel(BaseModel):
49 49 cls = Gist
50 vcs_backend = 'hg'
50 51
51 52 def _get_gist(self, gist):
52 53 """
@@ -145,7 +146,7 b' class GistModel(BaseModel):'
145 146 gist_repo_path = os.path.join(GIST_STORE_LOC, gist_id)
146 147 log.debug('Creating new %s GIST repo in %s', gist_type, gist_repo_path)
147 148 repo = RepoModel()._create_filesystem_repo(
148 repo_name=gist_id, repo_type='hg', repo_group=GIST_STORE_LOC,
149 repo_name=gist_id, repo_type=self.vcs_backend, repo_group=GIST_STORE_LOC,
149 150 use_global_config=True)
150 151
151 152 # now create single multifile commit
@@ -683,6 +683,7 b' class PullRequestModel(BaseModel):'
683 683
684 684 # source repo
685 685 source_repo = pull_request.source_repo.scm_instance()
686
686 687 try:
687 688 source_commit = source_repo.get_commit(commit_id=source_ref_name)
688 689 except CommitDoesNotExistError:
@@ -696,6 +697,7 b' class PullRequestModel(BaseModel):'
696 697
697 698 # target repo
698 699 target_repo = pull_request.target_repo.scm_instance()
700
699 701 try:
700 702 target_commit = target_repo.get_commit(commit_id=target_ref_name)
701 703 except CommitDoesNotExistError:
@@ -752,8 +754,8 b' class PullRequestModel(BaseModel):'
752 754 target_commit.raw_id, source_commit.raw_id, source_repo, merge=True,
753 755 pre_load=pre_load)
754 756
755 ancestor = target_repo.get_common_ancestor(
756 target_commit.raw_id, source_commit.raw_id, source_repo)
757 ancestor = source_repo.get_common_ancestor(
758 source_commit.raw_id, target_commit.raw_id, target_repo)
757 759
758 760 pull_request.source_ref = '%s:%s:%s' % (
759 761 source_ref_type, source_ref_name, source_commit.raw_id)
@@ -1314,10 +1316,21 b' class PullRequestModel(BaseModel):'
1314 1316 merge_state = self._refresh_merge_state(
1315 1317 pull_request, target_vcs, target_ref)
1316 1318 else:
1317 possible = pull_request.\
1318 last_merge_status == MergeFailureReason.NONE
1319 possible = pull_request.last_merge_status == MergeFailureReason.NONE
1320 metadata = {
1321 'target_ref': pull_request.target_ref_parts,
1322 'source_ref': pull_request.source_ref_parts,
1323 }
1324 if not possible and target_ref.type == 'branch':
1325 # NOTE(marcink): case for mercurial multiple heads on branch
1326 heads = target_vcs._heads(target_ref.name)
1327 if len(heads) != 1:
1328 heads = '\n,'.join(target_vcs._heads(target_ref.name))
1329 metadata.update({
1330 'heads': heads
1331 })
1319 1332 merge_state = MergeResponse(
1320 possible, False, None, pull_request.last_merge_status)
1333 possible, False, None, pull_request.last_merge_status, metadata=metadata)
1321 1334
1322 1335 return merge_state
1323 1336
@@ -1326,6 +1339,7 b' class PullRequestModel(BaseModel):'
1326 1339 name_or_id = reference.name
1327 1340 else:
1328 1341 name_or_id = reference.commit_id
1342
1329 1343 refreshed_commit = vcs_repository.get_commit(name_or_id)
1330 1344 refreshed_reference = Reference(
1331 1345 reference.type, reference.name, refreshed_commit.raw_id)
@@ -192,14 +192,14 b' class RepoModel(BaseModel):'
192 192 return repo_log
193 193
194 194 @classmethod
195 def update_repoinfo(cls, repositories=None):
195 def update_commit_cache(cls, repositories=None):
196 196 if not repositories:
197 197 repositories = Repository.getAll()
198 198 for repo in repositories:
199 199 repo.update_commit_cache()
200 200
201 201 def get_repos_as_dict(self, repo_list=None, admin=False,
202 super_user_actions=False):
202 super_user_actions=False, short_name=None):
203 203 _render = get_current_request().get_partial_renderer(
204 204 'rhodecode:templates/data_table/_dt_elements.mako')
205 205 c = _render.get_call_context()
@@ -208,8 +208,12 b' class RepoModel(BaseModel):'
208 208 return _render('quick_menu', repo_name)
209 209
210 210 def repo_lnk(name, rtype, rstate, private, archived, fork_of):
211 if short_name is not None:
212 short_name_var = short_name
213 else:
214 short_name_var = not admin
211 215 return _render('repo_name', name, rtype, rstate, private, archived, fork_of,
212 short_name=not admin, admin=False)
216 short_name=short_name_var, admin=False)
213 217
214 218 def last_change(last_change):
215 219 if admin and isinstance(last_change, datetime.datetime) and not last_change.tzinfo:
@@ -250,8 +254,8 b' class RepoModel(BaseModel):'
250 254 repo.private, repo.archived, repo.fork),
251 255 "name_raw": repo.repo_name.lower(),
252 256
253 "last_change": last_change(repo.last_db_change),
254 "last_change_raw": datetime_to_time(repo.last_db_change),
257 "last_change": last_change(repo.last_commit_change),
258 "last_change_raw": datetime_to_time(repo.last_commit_change),
255 259
256 260 "last_changeset": last_rev(repo.repo_name, cs_cache),
257 261 "last_changeset_raw": cs_cache.get('revision'),
@@ -97,6 +97,8 b' class RepoGroupModel(BaseModel):'
97 97 return string.Template(template).safe_substitute(
98 98 username=user.username,
99 99 user_id=user.user_id,
100 first_name=user.first_name,
101 last_name=user.last_name,
100 102 )
101 103
102 104 def create_personal_repo_group(self, user, commit_early=True):
@@ -307,6 +309,10 b' class RepoGroupModel(BaseModel):'
307 309 # trigger the post hook
308 310 from rhodecode.lib.hooks_base import log_create_repository_group
309 311 repo_group = RepoGroup.get_by_group_name(group_name)
312
313 # update repo group commit caches initially
314 repo_group.update_commit_cache()
315
310 316 log_create_repository_group(
311 317 created_by=user.username, **repo_group.get_dict())
312 318
@@ -684,6 +690,13 b' class RepoGroupModel(BaseModel):'
684 690 'revoked permission from usergroup: {} on repogroup: {}'.format(
685 691 group_name, repo_group), namespace='security.repogroup')
686 692
693 @classmethod
694 def update_commit_cache(cls, repo_groups=None):
695 if not repo_groups:
696 repo_groups = RepoGroup.getAll()
697 for repo_group in repo_groups:
698 repo_group.update_commit_cache()
699
687 700 def get_repo_groups_as_dict(self, repo_group_list=None, admin=False,
688 701 super_user_actions=False):
689 702
@@ -705,6 +718,11 b' class RepoGroupModel(BaseModel):'
705 718 (datetime.datetime.now() - datetime.datetime.utcnow()).seconds)
706 719 return _render("last_change", last_change)
707 720
721 def last_rev(repo_name, cs_cache):
722 return _render('revision', repo_name, cs_cache.get('revision'),
723 cs_cache.get('raw_id'), cs_cache.get('author'),
724 cs_cache.get('message'), cs_cache.get('date'))
725
708 726 def desc(desc, personal):
709 727 return _render(
710 728 'repo_group_desc', desc, personal, c.visual.stylify_metatags)
@@ -721,13 +739,19 b' class RepoGroupModel(BaseModel):'
721 739
722 740 repo_group_data = []
723 741 for group in repo_group_list:
742 cs_cache = group.changeset_cache
743 last_repo_name = cs_cache.get('source_repo_name')
724 744
725 745 row = {
726 746 "menu": quick_menu(group.group_name),
727 747 "name": repo_group_lnk(group.group_name),
728 748 "name_raw": group.group_name,
729 "last_change": last_change(group.last_db_change),
730 "last_change_raw": datetime_to_time(group.last_db_change),
749 "last_change": last_change(group.last_commit_change),
750 "last_change_raw": datetime_to_time(group.last_commit_change),
751
752 "last_changeset": "",
753 "last_changeset_raw": "",
754
731 755 "desc": desc(group.description_safe, group.personal),
732 756 "top_level_repos": 0,
733 757 "owner": user_profile(group.user.username)
@@ -818,6 +818,8 b' class ScmModel(BaseModel):'
818 818 repo_name=repo.repo_name, repo_alias=scm_instance.alias,
819 819 commit_ids=[tip.raw_id])
820 820
821 return tip
822
821 823 def delete_nodes(self, user, repo, message, nodes, parent_commit=None,
822 824 author=None, trigger_push_hook=True):
823 825 """
@@ -119,6 +119,7 b' class SettingsModel(BaseModel):'
119 119 new_ui.ui_value = val
120 120 new_ui.ui_active = active
121 121
122 repository_id = ''
122 123 if self.repo:
123 124 repo = self._get_repo(self.repo)
124 125 repository_id = repo.repo_id
@@ -440,26 +441,39 b' class VcsSettingsModel(object):'
440 441 HOOKS_SETTINGS = (
441 442 ('hooks', 'changegroup.repo_size'),
442 443 ('hooks', 'changegroup.push_logger'),
443 ('hooks', 'outgoing.pull_logger'),)
444 ('hooks', 'outgoing.pull_logger'),
445 )
444 446 HG_SETTINGS = (
445 447 ('extensions', 'largefiles'),
446 448 ('phases', 'publish'),
447 ('extensions', 'evolve'),)
449 ('extensions', 'evolve'),
450 ('extensions', 'topic'),
451 ('experimental', 'evolution'),
452 ('experimental', 'evolution.exchange'),
453 )
448 454 GIT_SETTINGS = (
449 ('vcs_git_lfs', 'enabled'),)
455 ('vcs_git_lfs', 'enabled'),
456 )
450 457 GLOBAL_HG_SETTINGS = (
451 458 ('extensions', 'largefiles'),
452 459 ('largefiles', 'usercache'),
453 460 ('phases', 'publish'),
454 461 ('extensions', 'hgsubversion'),
455 ('extensions', 'evolve'),)
462 ('extensions', 'evolve'),
463 ('extensions', 'topic'),
464 ('experimental', 'evolution'),
465 ('experimental', 'evolution.exchange'),
466 )
467
456 468 GLOBAL_GIT_SETTINGS = (
457 469 ('vcs_git_lfs', 'enabled'),
458 ('vcs_git_lfs', 'store_location'))
470 ('vcs_git_lfs', 'store_location')
471 )
459 472
460 473 GLOBAL_SVN_SETTINGS = (
461 474 ('vcs_svn_proxy', 'http_requests_enabled'),
462 ('vcs_svn_proxy', 'http_server_url'))
475 ('vcs_svn_proxy', 'http_server_url')
476 )
463 477
464 478 SVN_BRANCH_SECTION = 'vcs_svn_branch'
465 479 SVN_TAG_SECTION = 'vcs_svn_tag'
@@ -574,12 +588,38 b' class VcsSettingsModel(object):'
574 588 def create_repo_svn_settings(self, data):
575 589 return self._create_svn_settings(self.repo_settings, data)
576 590
591 def _set_evolution(self, settings, is_enabled):
592 if is_enabled:
593 # if evolve is active set evolution=all
594
595 self._create_or_update_ui(
596 settings, *('experimental', 'evolution'), value='all',
597 active=True)
598 self._create_or_update_ui(
599 settings, *('experimental', 'evolution.exchange'), value='yes',
600 active=True)
601 # if evolve is active set topics server support
602 self._create_or_update_ui(
603 settings, *('extensions', 'topic'), value='',
604 active=True)
605
606 else:
607 self._create_or_update_ui(
608 settings, *('experimental', 'evolution'), value='',
609 active=False)
610 self._create_or_update_ui(
611 settings, *('experimental', 'evolution.exchange'), value='no',
612 active=False)
613 self._create_or_update_ui(
614 settings, *('extensions', 'topic'), value='',
615 active=False)
616
577 617 @assert_repo_settings
578 618 def create_or_update_repo_hg_settings(self, data):
579 619 largefiles, phases, evolve = \
580 self.HG_SETTINGS
620 self.HG_SETTINGS[:3]
581 621 largefiles_key, phases_key, evolve_key = \
582 self._get_settings_keys(self.HG_SETTINGS, data)
622 self._get_settings_keys(self.HG_SETTINGS[:3], data)
583 623
584 624 self._create_or_update_ui(
585 625 self.repo_settings, *largefiles, value='',
@@ -587,21 +627,22 b' class VcsSettingsModel(object):'
587 627 self._create_or_update_ui(
588 628 self.repo_settings, *evolve, value='',
589 629 active=data[evolve_key])
630 self._set_evolution(self.repo_settings, is_enabled=data[evolve_key])
631
590 632 self._create_or_update_ui(
591 633 self.repo_settings, *phases, value=safe_str(data[phases_key]))
592 634
593 635 def create_or_update_global_hg_settings(self, data):
594 636 largefiles, largefiles_store, phases, hgsubversion, evolve \
595 = self.GLOBAL_HG_SETTINGS
637 = self.GLOBAL_HG_SETTINGS[:5]
596 638 largefiles_key, largefiles_store_key, phases_key, subversion_key, evolve_key \
597 = self._get_settings_keys(self.GLOBAL_HG_SETTINGS, data)
639 = self._get_settings_keys(self.GLOBAL_HG_SETTINGS[:5], data)
598 640
599 641 self._create_or_update_ui(
600 642 self.global_settings, *largefiles, value='',
601 643 active=data[largefiles_key])
602 644 self._create_or_update_ui(
603 self.global_settings, *largefiles_store,
604 value=data[largefiles_store_key])
645 self.global_settings, *largefiles_store, value=data[largefiles_store_key])
605 646 self._create_or_update_ui(
606 647 self.global_settings, *phases, value=safe_str(data[phases_key]))
607 648 self._create_or_update_ui(
@@ -609,9 +650,10 b' class VcsSettingsModel(object):'
609 650 self._create_or_update_ui(
610 651 self.global_settings, *evolve, value='',
611 652 active=data[evolve_key])
653 self._set_evolution(self.global_settings, is_enabled=data[evolve_key])
612 654
613 655 def create_or_update_repo_git_settings(self, data):
614 # NOTE(marcink): # comma make unpack work properly
656 # NOTE(marcink): # comma makes unpack work properly
615 657 lfs_enabled, \
616 658 = self.GIT_SETTINGS
617 659
@@ -675,6 +717,7 b' class VcsSettingsModel(object):'
675 717 def get_repo_ui_settings(self, section=None, key=None):
676 718 global_uis = self.global_settings.get_ui(section, key)
677 719 repo_uis = self.repo_settings.get_ui(section, key)
720
678 721 filtered_repo_uis = self._filter_ui_settings(repo_uis)
679 722 filtered_repo_uis_keys = [
680 723 (s.section, s.key) for s in filtered_repo_uis]
@@ -24,10 +24,15 b' import traceback'
24 24 import sshpubkeys
25 25 import sshpubkeys.exceptions
26 26
27 from cryptography.hazmat.primitives.asymmetric import rsa
28 from cryptography.hazmat.primitives import serialization as crypto_serialization
29 from cryptography.hazmat.backends import default_backend as crypto_default_backend
30
27 31 from rhodecode.model import BaseModel
28 32 from rhodecode.model.db import UserSshKeys
29 33 from rhodecode.model.meta import Session
30 34
35
31 36 log = logging.getLogger(__name__)
32 37
33 38
@@ -62,16 +67,24 b' class SshKeyModel(BaseModel):'
62 67 raise
63 68
64 69 def generate_keypair(self, comment=None):
65 from Crypto.PublicKey import RSA
66
67 key = RSA.generate(2048)
68 private = key.exportKey('PEM')
69 70
70 pubkey = key.publickey()
71 public = pubkey.exportKey('OpenSSH')
71 key = rsa.generate_private_key(
72 backend=crypto_default_backend(),
73 public_exponent=65537,
74 key_size=2048
75 )
76 private_key = key.private_bytes(
77 crypto_serialization.Encoding.PEM,
78 crypto_serialization.PrivateFormat.PKCS8,
79 crypto_serialization.NoEncryption())
80 public_key = key.public_key().public_bytes(
81 crypto_serialization.Encoding.OpenSSH,
82 crypto_serialization.PublicFormat.OpenSSH
83 )
84
72 85 if comment:
73 public = public + " " + comment
74 return private, public
86 public_key = public_key + " " + comment
87 return private_key, public_key
75 88
76 89 def create(self, user, fingerprint, key_data, description):
77 90 """
@@ -14,11 +14,11 b' input[type="button"] {'
14 14 font-family: @text-light;
15 15 text-decoration: none;
16 16 text-shadow: none;
17 color: @grey4;
17 color: @grey2;
18 18 background-color: white;
19 19 background-image: none;
20 20 border: none;
21 .border ( @border-thickness-buttons, @grey4 );
21 .border ( @border-thickness-buttons, @grey5 );
22 22 .border-radius (@border-radius);
23 23 cursor: pointer;
24 24 white-space: nowrap;
@@ -26,6 +26,10 b' input[type="button"] {'
26 26 -moz-transition: background .3s,color .3s;
27 27 -o-transition: background .3s,color .3s;
28 28 transition: background .3s,color .3s;
29 box-shadow: @button-shadow;
30 -webkit-box-shadow: @button-shadow;
31
32
29 33
30 34 a {
31 35 display: block;
@@ -44,8 +48,9 b' input[type="button"] {'
44 48 outline:none;
45 49 }
46 50 &:hover {
47 color: white;
48 background-color: @grey4;
51 color: @rcdarkblue;
52 background-color: @white;
53 .border ( @border-thickness, @grey4 );
49 54 }
50 55
51 56 .icon-remove-sign {
@@ -70,26 +75,26 b' input[type="button"] {'
70 75
71 76
72 77 .btn-default {
73 .border ( @border-thickness-buttons, @rcblue );
78 border: @border-thickness solid @grey5;
74 79 background-image: none;
75 color: @rcblue;
80 color: @grey2;
76 81
77 82 a {
78 color: @rcblue;
83 color: @grey2;
79 84 }
80 85
81 86 &:hover,
82 87 &.active {
83 color: white;
84 background-color: @rcdarkblue;
85 .border ( @border-thickness, @rcdarkblue );
88 color: @rcdarkblue;
89 background-color: @white;
90 .border ( @border-thickness, @grey4 );
86 91
87 92 a {
88 color: white;
93 color: @grey2;
89 94 }
90 95 }
91 96 &:disabled {
92 .border ( @border-thickness-buttons, @grey4 );
97 .border ( @border-thickness-buttons, @grey5 );
93 98 background-color: transparent;
94 99 }
95 100 }
@@ -326,6 +331,7 b' input[type="submit"] {'
326 331 .border ( @border-thickness-buttons, @rcblue );
327 332 background-color: @rcblue;
328 333 color: white;
334 opacity: 0.5;
329 335 }
330 336 }
331 337
@@ -416,3 +422,23 b' input[type="reset"] {'
416 422 }
417 423 }
418 424
425
426 .button-links {
427 float: left;
428 display: inline;
429 margin: 0;
430 padding-left: 0;
431 list-style: none;
432 text-align: right;
433
434 li {
435
436
437 }
438
439 li.active {
440 background-color: @grey6;
441 .border ( @border-thickness, @grey4 );
442 }
443
444 }
@@ -404,12 +404,9 b' div.codeblock {'
404 404
405 405 // TODO: johbo: Added interim to get rid of the margin around
406 406 // Select2 widgets. This needs further cleanup.
407 margin-top: @padding;
408
409 407 overflow: auto;
410 408 padding: 0px;
411 border: @border-thickness solid @grey5;
412 background: @grey6;
409 border: @border-thickness solid @grey6;
413 410 .border-radius(@border-radius);
414 411
415 412 #remove_gist {
@@ -479,7 +476,7 b' div.codeblock {'
479 476 }
480 477
481 478 .code-body {
482 padding: @padding;
479 padding: 0.8em 1em;
483 480 background-color: #ffffff;
484 481 min-width: 100%;
485 482 box-sizing: border-box;
@@ -492,6 +489,21 b' div.codeblock {'
492 489 height: auto;
493 490 width: 100%;
494 491 }
492
493 .markdown-block {
494 padding: 1em 0;
495 }
496 }
497
498 .codeblock-header {
499 background: @grey7;
500 height: 36px;
501 }
502
503 .path {
504 border-bottom: 1px solid @grey6;
505 padding: .65em 1em;
506 height: 18px;
495 507 }
496 508 }
497 509
@@ -27,7 +27,7 b''
27 27
28 28 .CodeMirror-gutters {
29 29 border-right: 1px solid #ddd;
30 background-color: @grey6;
30 background-color: white;
31 31 white-space: nowrap;
32 32 }
33 33 .CodeMirror-linenumbers {}
@@ -14,7 +14,7 b' tr.inline-comments div {'
14 14 max-width: 100%;
15 15
16 16 p {
17 white-space: normal;
17 white-space: normal;
18 18 }
19 19
20 20 code, pre, .code, dd {
@@ -227,7 +227,7 b' tr.inline-comments div {'
227 227 .delete-comment {
228 228 display: inline-block;
229 229 color: @rcblue;
230
230
231 231 &:hover {
232 232 cursor: pointer;
233 233 }
@@ -377,13 +377,13 b' form.comment-form {'
377 377 position: relative;
378 378 width: 100%;
379 379 min-height: 42px;
380
380
381 381 .status_box,
382 382 .cancel-button {
383 383 float: left;
384 384 display: inline-block;
385 385 }
386
386
387 387 .action-buttons {
388 388 float: right;
389 389 display: inline-block;
@@ -426,10 +426,10 b' form.comment-form {'
426 426
427 427 .comment-form-login {
428 428 .comment-help {
429 padding: 0.9em; //same as the button
429 padding: 0.7em; //same as the button
430 430 }
431 431
432 div.clearfix {
432 div.clearfix {
433 433 clear: both;
434 434 width: 100%;
435 435 display: block;
@@ -38,7 +38,7 b''
38 38
39 39 .form-control {
40 40 width: 100%;
41 padding: 0.9em;
41 padding: 0.7em;
42 42 border: 1px solid #979797;
43 43 border-radius: 2px;
44 44 }
@@ -60,13 +60,13 b' form.rcform {'
60 60 max-width: 500px;
61 61 margin: 0 0 @padding -@legend-width;
62 62 padding: 0 0 0 @legend-width;
63
63
64 64 .btn {
65 65 display: inline-block;
66 66 margin: 0 1em @padding 0;
67 67 }
68 68 }
69
69
70 70 input,
71 71 textarea {
72 72 float: left;
@@ -113,7 +113,7 b' form.rcform {'
113 113 opacity: 0.5;
114 114 }
115 115 }
116
116
117 117 input[type="radio"]:not(#ie),
118 118 input[type="checkbox"]:not(#ie) {
119 119 // Hide the input, but have it still be clickable
@@ -187,13 +187,13 b' form.rcform {'
187 187 filter: progid:DXImageTransform.Microsoft.Matrix(sizingMethod='auto expand', M11=0.7071067811865476, M12=-0.7071067811865475, M21=0.7071067811865475, M22=0.7071067811865476); /* IE6,IE7 */
188 188
189 189 -ms-filter: "progid:DXImageTransform.Microsoft.Matrix(SizingMethod='auto expand', M11=0.7071067811865476, M12=-0.7071067811865475, M21=0.7071067811865475, M22=0.7071067811865476)"; /* IE8 */ }
190
190
191 191 & + .label {
192 192 float: left;
193 193 margin-top: 5px
194 194 }
195 195 }
196
196
197 197 input[type=checkbox]:not(#ie) {
198 198 visibility: hidden;
199 199 &:checked + label:after {
@@ -231,6 +231,11 b' form.rcform {'
231 231
232 232 .drop-menu {
233 233 float: left;
234
235 & + .last-item {
236 margin: 0;
237 }
238
234 239 margin: 0 @input-padding 0 0;
235 240 }
236 241
@@ -244,7 +249,7 b' form.rcform {'
244 249 .error-message {
245 250 margin-top: 5px;
246 251 }
247
252
248 253 input[type=submit] {
249 254 &:extend(.btn-primary);
250 255
@@ -271,14 +276,15 b' form.rcform {'
271 276 .badged-field {
272 277 .user-badge {
273 278 line-height: 25px;
274 padding: 10px 5px;
279 padding: .4em;
275 280 border-radius: @border-radius;
276 border-top: 1px solid @rclightblue;
277 border-left: 1px solid @rclightblue;
278 border-bottom: 1px solid @rclightblue;
281 border-top: 1px solid @grey4;
282 border-left: 1px solid @grey4;
283 border-bottom: 1px solid @grey4;
279 284 font-size: 14px;
280 285 font-style: normal;
281 286 color: @text-light;
287 background: @grey7;
282 288 display: inline-block;
283 289 vertical-align: top;
284 290 cursor: default;
@@ -212,6 +212,13 b' div.markdown-block strong {'
212 212 margin: 0;
213 213 }
214 214
215 div.markdown-block ul.checkbox,
216 div.markdown-block ol.checkbox {
217 padding-left: 20px !important;
218 margin-top: 0px !important;
219 margin-bottom: 18px !important;
220 }
221
215 222 div.markdown-block ul,
216 223 div.markdown-block ol {
217 224 padding-left: 30px !important;
@@ -219,6 +226,13 b' div.markdown-block ol {'
219 226 margin-bottom: 18px !important;
220 227 }
221 228
229 div.markdown-block ul.checkbox li,
230 div.markdown-block ol.checkbox li {
231 list-style: none !important;
232 margin: 6px !important;
233 padding: 0 !important;
234 }
235
222 236 div.markdown-block ul li,
223 237 div.markdown-block ol li {
224 238 list-style: disc !important;
@@ -95,7 +95,7 b''
95 95 margin: 0 1em @padding 0;
96 96 }
97 97 }
98
98
99 99 .checkbox {
100 100 display: inline;
101 101 width: auto;
@@ -198,15 +198,16 b''
198 198 }
199 199
200 200 .user-menu.submenu {
201 right: 0;
202 left: auto;
201 right: 0!important;
202 left: auto!important;
203 203 min-width: 290px;
204 204 }
205 205
206
207 206 .user-menu {
208 207 .bookmark-items {
209 padding: 4px 2px;
208 border-top: @border-thickness solid @grey6;
209 margin-top: 1em;
210 padding: 1em .5em;
210 211 color: @grey3;
211 212 border-bottom: @grey3;
212 213
@@ -227,8 +228,10 b''
227 228 padding: @menupadding;
228 229 z-index: 999;
229 230 overflow: hidden;
230 background-color: @grey6;
231 background-color: @white;
232 border: 1px solid @grey5;
231 233 color: @grey2;
234 box-shadow: @dropdown-shadow;
232 235
233 236 h4 {
234 237 margin-bottom: 12px;
@@ -261,7 +264,7 b''
261 264 .buttons .register {
262 265 a {
263 266 color: @rcblue;
264
267
265 268 &:hover {
266 269 color: @rcdarkblue;
267 270 }
@@ -289,15 +292,16 b''
289 292 .big_gravatar {
290 293 float: left;
291 294 display: block;
292 margin-top: .5em;
295 padding: .5em;
293 296 }
294 297
295 .full_name,
296 .email {
297 margin: 0 0 0 65px;
298 .full_name {
299 margin: 0 0 0 70px;
300 padding-top: 1em;
298 301 }
299 302
300 303 .email {
304 margin: 0 0 0 70px;
301 305 font-family: @text-light;
302 306 }
303 307
@@ -307,8 +311,6 b''
307 311 padding: @padding 0 0 0;
308 312
309 313 li {
310 border-top: @border-thickness solid @grey5;
311
312 314 input {
313 315 margin: @padding 0 0 0;
314 316 }
@@ -107,6 +107,12 b' input + .action-link, .action-link.first'
107 107
108 108 .clipboard-action {
109 109 cursor: pointer;
110 color: @grey4;
111 margin-left: 5px;
112
113 &:hover {
114 color: @grey2;
115 }
110 116 }
111 117
112 118 ul.simple-list{
@@ -237,7 +243,7 b' input.inline[type="file"] {'
237 243 position: relative;
238 244 vertical-align: bottom;
239 245 padding: 0 @header-padding;
240 background-color: @grey2;
246 background-color: @grey1;
241 247 color: @grey5;
242 248
243 249 .title {
@@ -271,7 +277,9 b' input.inline[type="file"] {'
271 277 // Gists
272 278 #files_data {
273 279 clear: both; //for firefox
280 padding-top: 10px;
274 281 }
282
275 283 #gistid {
276 284 margin-right: @padding;
277 285 }
@@ -516,7 +524,7 b' ul.auth_plugins {'
516 524 text-align: center;
517 525 vertical-align: middle;
518 526 color: @grey2;
519 background-color: @grey6;
527 font-size: 11px;
520 528
521 529 p {
522 530 margin: 0;
@@ -605,10 +613,20 b' button.close {'
605 613 }
606 614
607 615
608 input {
616 input, textarea {
609 617 &.disabled {
610 618 opacity: .5;
611 619 }
620
621 &:hover {
622 border-color: @grey3;
623 box-shadow: @button-shadow;
624 }
625
626 &:focus {
627 border-color: @rcblue;
628 box-shadow: @button-shadow;
629 }
612 630 }
613 631
614 632 // remove extra padding in firefox
@@ -643,16 +661,20 b' select {'
643 661 padding: 0 18px 0 8px;
644 662 line-height:1em;
645 663 font-size: @basefontsize;
646 border: @border-thickness solid @rcblue;
664 border: @border-thickness solid @grey5;
665 border-radius: @border-radius;
647 666 background:white url("../images/dt-arrow-dn.png") no-repeat 100% 50%;
648 color: @rcblue;
667 color: @grey4;
668 box-shadow: @button-shadow;
649 669
650 670 &:after {
651 671 content: "\00A0\25BE";
652 672 }
653 673
654 &:focus {
674 &:focus, &:hover {
655 675 outline: none;
676 border-color: @grey4;
677 color: @rcdarkblue;
656 678 }
657 679 }
658 680
@@ -712,8 +734,8 b' label {'
712 734 margin: -5px 0;
713 735 padding: 0;
714 736 line-height: 1em;
715 border: 1px solid @grey4;
716 737 box-sizing: content-box;
738 border-radius: 50%;
717 739
718 740 &.gravatar-large {
719 741 margin: -0.5em .25em -0.5em 0;
@@ -938,9 +960,6 b' label {'
938 960 }
939 961
940 962
941 #graph_nodes {
942 padding-top: 43px;
943 }
944 963
945 964 #graph_content{
946 965
@@ -973,13 +992,12 b' label {'
973 992 }
974 993
975 994 .graph-col-wrapper {
976 padding-left: 110px;
977 995
978 996 #graph_nodes {
979 997 width: 100px;
980 margin-left: -110px;
981 float: left;
982 clear: left;
998 position: absolute;
999 left: 70px;
1000 z-index: -1;
983 1001 }
984 1002 }
985 1003
@@ -996,6 +1014,16 b' label {'
996 1014 }
997 1015 }
998 1016
1017 .obsolete-toggle {
1018 line-height: 30px;
1019 margin-left: -15px;
1020 }
1021
1022 #rev_range_container, #rev_range_clear, #rev_range_more {
1023 margin-top: -5px;
1024 margin-bottom: -5px;
1025 }
1026
999 1027 #filter_changelog {
1000 1028 float: left;
1001 1029 }
@@ -1024,11 +1052,15 b' label {'
1024 1052 float:left;
1025 1053 }
1026 1054
1027 .branding{
1055 .branding {
1028 1056 float: left;
1029 1057 padding: 9px 2px;
1030 1058 line-height: 1em;
1031 1059 font-size: @navigation-fontsize;
1060
1061 a {
1062 color: @grey5
1063 }
1032 1064 }
1033 1065
1034 1066 img {
@@ -1047,7 +1079,7 b' label {'
1047 1079 }
1048 1080
1049 1081 .flag_status {
1050 margin: 2px 8px 6px 2px;
1082 margin: 2px;
1051 1083 &.under_review {
1052 1084 .circle(5px, @alert3);
1053 1085 }
@@ -1218,24 +1250,37 b' table.integrations {'
1218 1250
1219 1251 .autocomplete-suggestions {
1220 1252 width: auto !important; // overrides autocomplete.js
1253 min-width: 278px;
1221 1254 margin: 0;
1222 border: @border-thickness solid @rcblue;
1255 border: @border-thickness solid @grey5;
1223 1256 border-radius: @border-radius;
1224 color: @rcblue;
1257 color: @grey2;
1225 1258 background-color: white;
1226 1259 }
1260
1261 .autocomplete-qfilter-suggestions {
1262 width: auto !important; // overrides autocomplete.js
1263 max-height: 100% !important;
1264 min-width: 376px;
1265 margin: 0;
1266 border: @border-thickness solid @grey5;
1267 color: @grey2;
1268 background-color: white;
1269 }
1270
1227 1271 .autocomplete-selected {
1228 1272 background: #F0F0F0;
1229 1273 }
1274
1230 1275 .ac-container-wrap {
1231 1276 margin: 0;
1232 1277 padding: 8px;
1233 border-bottom: @border-thickness solid @rclightblue;
1278 border-bottom: @border-thickness solid @grey5;
1234 1279 list-style-type: none;
1235 1280 cursor: pointer;
1236 1281
1237 1282 &:hover {
1238 background-color: @rclightblue;
1283 background-color: @grey7;
1239 1284 }
1240 1285
1241 1286 img {
@@ -1290,9 +1335,9 b' table.integrations {'
1290 1335 }
1291 1336 }
1292 1337
1293 #editor_container{
1294 position: relative;
1295 margin: @padding;
1338 #editor_container {
1339 position: relative;
1340 margin: @padding 10px;
1296 1341 }
1297 1342 }
1298 1343
@@ -1796,7 +1841,6 b' BIN_FILENODE = 7'
1796 1841 }
1797 1842
1798 1843 #changeset_compare_view_content {
1799 margin-bottom: @space;
1800 1844 clear: both;
1801 1845 width: 100%;
1802 1846 box-sizing: border-box;
@@ -2027,15 +2071,15 b' BIN_FILENODE = 7'
2027 2071
2028 2072 // Files
2029 2073 .edit-file-title {
2030 border-bottom: @border-thickness solid @border-default-color;
2031
2032 .breadcrumbs {
2033 margin-bottom: 0;
2074 font-size: 16px;
2075
2076 .title-heading {
2077 padding: 2px;
2034 2078 }
2035 2079 }
2036 2080
2037 2081 .edit-file-fieldset {
2038 margin-top: @sidebarpadding;
2082 margin: @sidebarpadding 0;
2039 2083
2040 2084 .fieldset {
2041 2085 .left-label {
@@ -2080,8 +2124,29 b' BIN_FILENODE = 7'
2080 2124 .new-file,
2081 2125 #filter_activate,
2082 2126 #filter_deactivate {
2083 float: left;
2084 margin: 0 0 0 15px;
2127 float: right;
2128 margin: 0 0 0 10px;
2129 }
2130
2131 .file-upload-transaction-wrapper {
2132 margin-top: 57px;
2133 clear: both;
2134 }
2135
2136 .file-upload-transaction-wrapper .error {
2137 color: @color5;
2138 }
2139
2140 .file-upload-transaction {
2141 min-height: 200px;
2142 padding: 54px;
2143 border: 1px solid @grey5;
2144 text-align: center;
2145 clear: both;
2146 }
2147
2148 .file-upload-transaction i {
2149 font-size: 48px
2085 2150 }
2086 2151
2087 2152 h3.files_location{
@@ -2089,11 +2154,12 b' h3.files_location{'
2089 2154 }
2090 2155
2091 2156 .browser-nav {
2157 width: 100%;
2092 2158 display: table;
2093 margin-bottom: @space;
2094
2159 margin-bottom: 20px;
2095 2160
2096 2161 .info_box {
2162 float: left;
2097 2163 display: inline-table;
2098 2164 height: 2.5em;
2099 2165
@@ -2102,36 +2168,58 b' h3.files_location{'
2102 2168 vertical-align: middle;
2103 2169 }
2104 2170
2171 .drop-menu {
2172 margin: 0 10px;
2173 }
2174
2105 2175 .info_box_elem {
2106 border-top: @border-thickness solid @rcblue;
2107 border-bottom: @border-thickness solid @rcblue;
2176 border-top: @border-thickness solid @grey5;
2177 border-bottom: @border-thickness solid @grey5;
2178 box-shadow: @button-shadow;
2108 2179
2109 2180 #at_rev, a {
2110 padding: 0.6em 0.9em;
2181 padding: 0.6em 0.4em;
2111 2182 margin: 0;
2112 2183 .box-shadow(none);
2113 2184 border: 0;
2114 2185 height: 12px;
2186 color: @grey2;
2115 2187 }
2116 2188
2117 2189 input#at_rev {
2118 2190 max-width: 50px;
2119 text-align: right;
2191 text-align: center;
2120 2192 }
2121 2193
2122 2194 &.previous {
2123 border: @border-thickness solid @rcblue;
2195 border: @border-thickness solid @grey5;
2196 border-top-left-radius: @border-radius;
2197 border-bottom-left-radius: @border-radius;
2198
2199 &:hover {
2200 border-color: @grey4;
2201 }
2202
2124 2203 .disabled {
2125 color: @grey4;
2204 color: @grey5;
2126 2205 cursor: not-allowed;
2206 opacity: 0.5;
2127 2207 }
2128 2208 }
2129 2209
2130 2210 &.next {
2131 border: @border-thickness solid @rcblue;
2211 border: @border-thickness solid @grey5;
2212 border-top-right-radius: @border-radius;
2213 border-bottom-right-radius: @border-radius;
2214
2215 &:hover {
2216 border-color: @grey4;
2217 }
2218
2132 2219 .disabled {
2133 color: @grey4;
2220 color: @grey5;
2134 2221 cursor: not-allowed;
2222 opacity: 0.5;
2135 2223 }
2136 2224 }
2137 2225 }
@@ -2148,8 +2236,14 b' h3.files_location{'
2148 2236 margin-right: @padding;
2149 2237 }
2150 2238 }
2239
2151 2240 }
2152 2241
2242 .select-index-number {
2243 margin: 0 0 0 20px;
2244 color: @grey3;
2245 }
2246
2153 2247 .search_activate {
2154 2248 display: table-cell;
2155 2249 vertical-align: middle;
@@ -2178,26 +2272,54 b' h3.files_location{'
2178 2272 margin: -25px 0px 5px 0px;
2179 2273 }
2180 2274
2181 .node-filter {
2182 font-size: @repo-title-fontsize;
2183 padding: 4px 0px 0px 0px;
2184
2185 .node-filter-path {
2186 float: left;
2187 color: @grey4;
2275 .files-quick-filter {
2276 float: right;
2277 width: 180px;
2278 position: relative;
2279 }
2280
2281 .files-filter-box {
2282 display: flex;
2283 padding: 0px;
2284 border-radius: 3px;
2285 margin-bottom: 0;
2286
2287 a {
2288 border: none !important;
2289 }
2290
2291 li {
2292 list-style-type: none
2293 }
2294 }
2295
2296 .files-filter-box-path {
2297 line-height: 33px;
2298 padding: 0;
2299 width: 20px;
2300 position: absolute;
2301 z-index: 11;
2302 left: 5px;
2303 }
2304
2305 .files-filter-box-input {
2306 margin-right: 0;
2307
2308 input {
2309 border: 1px solid @white;
2310 padding-left: 25px;
2311 width: 145px;
2312
2313 &:hover {
2314 border-color: @grey6;
2188 2315 }
2189 .node-filter-input {
2190 float: left;
2191 margin: -2px 0px 0px 2px;
2192 input {
2193 padding: 2px;
2194 border: none;
2195 font-size: @repo-title-fontsize;
2196 }
2316
2317 &:focus {
2318 border-color: @grey5;
2197 2319 }
2320 }
2198 2321 }
2199 2322
2200
2201 2323 .browser-result{
2202 2324 td a{
2203 2325 margin-left: 0.5em;
@@ -2215,6 +2337,142 b' h3.files_location{'
2215 2337 }
2216 2338
2217 2339
2340 .edit-file-fieldset #location,
2341 .edit-file-fieldset #filename {
2342 display: flex;
2343 width: -moz-available; /* WebKit-based browsers will ignore this. */
2344 width: -webkit-fill-available; /* Mozilla-based browsers will ignore this. */
2345 width: fill-available;
2346 border: 0;
2347 }
2348
2349 .path-items {
2350 display: flex;
2351 padding: 0;
2352 border: 1px solid #eeeeee;
2353 width: 100%;
2354 float: left;
2355
2356 .breadcrumb-path {
2357 line-height: 30px;
2358 padding: 0 4px;
2359 white-space: nowrap;
2360 }
2361
2362 .location-path {
2363 width: -moz-available; /* WebKit-based browsers will ignore this. */
2364 width: -webkit-fill-available; /* Mozilla-based browsers will ignore this. */
2365 width: fill-available;
2366
2367 .file-name-input {
2368 padding: 0.5em 0;
2369 }
2370
2371 }
2372
2373 ul {
2374 display: flex;
2375 margin: 0;
2376 padding: 0;
2377 width: 100%;
2378 }
2379
2380 li {
2381 list-style-type: none;
2382 }
2383
2384 }
2385
2386 .editor-items {
2387 height: 40px;
2388 margin: 10px 0 -17px 10px;
2389
2390 .editor-action {
2391 cursor: pointer;
2392 }
2393
2394 .editor-action.active {
2395 border-bottom: 2px solid #5C5C5C;
2396 }
2397
2398 li {
2399 list-style-type: none;
2400 }
2401 }
2402
2403 .edit-file-fieldset .message textarea {
2404 border: 1px solid #eeeeee;
2405 }
2406
2407 #files_data .codeblock {
2408 background-color: #F5F5F5;
2409 }
2410
2411 #editor_preview {
2412 background: white;
2413 }
2414
2415 .show-editor {
2416 padding: 10px;
2417 background-color: white;
2418
2419 }
2420
2421 .show-preview {
2422 padding: 10px;
2423 background-color: white;
2424 border-left: 1px solid #eeeeee;
2425 }
2426 // quick filter
2427 .grid-quick-filter {
2428 float: right;
2429 position: relative;
2430 }
2431
2432 .grid-filter-box {
2433 display: flex;
2434 padding: 0px;
2435 border-radius: 3px;
2436 margin-bottom: 0;
2437
2438 a {
2439 border: none !important;
2440 }
2441
2442 li {
2443 list-style-type: none
2444 }
2445 }
2446
2447 .grid-filter-box-icon {
2448 line-height: 33px;
2449 padding: 0;
2450 width: 20px;
2451 position: absolute;
2452 z-index: 11;
2453 left: 5px;
2454 }
2455
2456 .grid-filter-box-input {
2457 margin-right: 0;
2458
2459 input {
2460 border: 1px solid @white;
2461 padding-left: 25px;
2462 width: 145px;
2463
2464 &:hover {
2465 border-color: @grey6;
2466 }
2467
2468 &:focus {
2469 border-color: @grey5;
2470 }
2471 }
2472 }
2473
2474
2475
2218 2476 // Search
2219 2477
2220 2478 .search-form{
@@ -2277,7 +2535,7 b' div.search-code-body {'
2277 2535 }
2278 2536
2279 2537 .code-body {
2280 border: @border-thickness solid @border-default-color;
2538 border: @border-thickness solid @grey6;
2281 2539 .border-radius(@border-radius);
2282 2540 }
2283 2541
@@ -2297,6 +2555,11 b' div.search-code-body {'
2297 2555 .break { background-color: #DDE7EF; width: 100%; color: #747474; display: block; }
2298 2556 }
2299 2557
2558 .path {
2559 border-bottom: none !important;
2560 border-left: 1px solid @grey6 !important;
2561 border-right: 1px solid @grey6 !important;
2562 }
2300 2563 }
2301 2564
2302 2565 table.rctable td.td-search-results div {
@@ -2472,3 +2735,56 b' form.markup-form {'
2472 2735 padding: 20px;
2473 2736 background-color: white;
2474 2737 }
2738
2739
2740 .dropzone-wrapper {
2741 border: 1px solid @grey5;
2742 padding: 20px;
2743 }
2744
2745 .dropzone,
2746 .dropzone-pure {
2747 border: 2px dashed @grey5;
2748 border-radius: 5px;
2749 background: white;
2750 min-height: 200px;
2751 padding: 54px;
2752
2753 .dz-message {
2754 font-weight: 700;
2755 text-align: center;
2756 margin: 2em 0;
2757 }
2758
2759 }
2760
2761 .dz-preview {
2762 margin: 10px 0 !important;
2763 position: relative;
2764 vertical-align: top;
2765 padding: 10px;
2766 border-bottom: 1px solid @grey5;
2767 }
2768
2769 .dz-filename {
2770 font-weight: 700;
2771 float:left;
2772 }
2773
2774 .dz-sending {
2775 float: right;
2776 }
2777
2778 .dz-response {
2779 clear:both
2780 }
2781
2782 .dz-filename-size {
2783 float:right
2784 }
2785
2786 .dz-error-message {
2787 color: @alert2;
2788 padding-top: 10px;
2789 clear: both;
2790 }
@@ -2,10 +2,21 b''
2 2 // For use in RhodeCode applications;
3 3 // see style guide documentation for guidelines.
4 4
5 // TOP MAIN DARK NAVIGATION
6
7 .header .main_nav.horizontal-list {
8 float: right;
9 color: @grey4;
10 > li {
11 a {
12 color: @grey4;
13 }
14 }
15 }
16
5 17 // HEADER NAVIGATION
6 18
7 19 .horizontal-list {
8 float: right;
9 20 display: block;
10 21 margin: 0;
11 22 padding: 0;
@@ -18,6 +29,7 b''
18 29 li {
19 30 line-height: 1em;
20 31 list-style-type: none;
32 margin: 0 20px 0 0;
21 33
22 34 a {
23 35 padding: 0 .5em;
@@ -55,12 +67,6 b''
55 67 .user {
56 68 padding-bottom: 10px;
57 69 }
58
59 &.open {
60 .user {
61 border-bottom: 5px solid @rcblue;
62 }
63 }
64 70 }
65 71
66 72 &:before { content: none; }
@@ -80,10 +86,6 b''
80 86 }
81 87 }
82 88
83 &.active {
84 border-bottom: 5px solid @rcblue;
85 }
86
87 89 &.open {
88 90
89 91 a {
@@ -118,14 +120,12 b''
118 120 > a,
119 121 &.has_select2 a {
120 122 display: block;
121 padding: 10px 0 2px;
123 padding: 10px 0;
122 124 }
123 125
124 126 .menulabel {
125 padding: 0 .5em;
126 127 line-height: 1em;
127 128 // for this specifically we do not use a variable
128 border-right: 1px solid @grey4;
129 129 }
130 130
131 131 .pr_notifications {
@@ -141,7 +141,7 b''
141 141 &.open,
142 142 &.active {
143 143 a {
144 color: @grey1;
144 color: @rcblue;
145 145 }
146 146 }
147 147 }
@@ -156,6 +156,14 b''
156 156 position: relative;
157 157 }
158 158
159 .menulink {
160 &.disabled {
161 color: @grey3;
162 cursor: default;
163 opacity: 0.5;
164 }
165 }
166
159 167 #quick_login {
160 168
161 169 li a {
@@ -281,16 +289,19 b''
281 289 }
282 290
283 291 .navigation li:last-child .submenu {
284 right: -20px;
285 left: auto;
292 right: auto;
293 left: 0;
294 border: 1px solid @grey5;
295 background: @white;
296 box-shadow: @dropdown-shadow;
286 297 }
287 298
288 299 .submenu {
289 300 position: absolute;
290 301 top: 100%;
291 302 left: 0;
292 min-width: 150px;
293 margin: 6px 0 0;
303 min-width: 180px;
304 margin: 2px 0 0;
294 305 padding: 0;
295 306 text-align: left;
296 307 font-family: @text-light;
@@ -303,7 +314,7 b''
303 314 padding: 0 .5em;
304 315 line-height: 1em;
305 316 color: @grey3;
306 background-color: @grey6;
317 background-color: @white;
307 318 list-style-type: none;
308 319
309 320 a {
@@ -324,7 +335,7 b''
324 335 z-index: 30;
325 336 }
326 337 &:hover {
327 background-color: @grey5;
338 background-color: @grey7;
328 339 -webkit-transition: background .3s;
329 340 -moz-transition: background .3s;
330 341 -o-transition: background .3s;
@@ -501,10 +512,10 b''
501 512
502 513 #context-bar {
503 514 display: block;
504 margin: 0 auto;
515 margin: 0 auto 20px 0;
505 516 padding: 0 @header-padding;
506 background-color: @grey6;
507 border-bottom: @border-thickness solid @grey5;
517 background-color: @grey7;
518 border-bottom: 1px solid @grey5;
508 519
509 520 .clear {
510 521 clear: both;
@@ -513,19 +524,22 b''
513 524
514 525 ul#context-pages {
515 526 li {
516 line-height: 1em;
517 527 list-style-type: none;
518 528
519 529 a {
520 color: @grey3;
530 color: @grey2;
531
532 &:hover {
533 color: @grey1;
534 }
521 535 }
522 536
523 537 &.active {
524 538 // special case, non-variable color
525 border-bottom: 4px solid @nav-grey;
539 border-bottom: 2px solid @rcblue;
526 540
527 541 a {
528 color: @grey1;
542 color: @rcblue;
529 543 }
530 544 }
531 545 }
@@ -534,8 +548,9 b' ul#context-pages {'
534 548 // PAGINATION
535 549
536 550 .pagination {
537 border: @border-thickness solid @rcblue;
538 color: @rcblue;
551 border: @border-thickness solid @grey5;
552 color: @grey2;
553 box-shadow: @button-shadow;
539 554
540 555 .current {
541 556 color: @grey4;
@@ -552,33 +567,44 b' ul#context-pages {'
552 567 .dataTables_paginate, .pagination-wh {
553 568 text-align: left;
554 569 display: inline-block;
555 border-left: 1px solid @rcblue;
570 border-left: 1px solid @grey5;
556 571 float: none;
557 572 overflow: hidden;
573 box-shadow: @button-shadow;
558 574
559 575 .paginate_button, .pager_curpage,
560 576 .pager_link, .pg-previous, .pg-next, .pager_dotdot {
561 577 display: inline-block;
562 578 padding: @menupadding/4 @menupadding;
563 border: 1px solid @rcblue;
579 border: 1px solid @grey5;
564 580 border-left: 0;
565 color: @rcblue;
581 color: @grey2;
566 582 cursor: pointer;
567 583 float: left;
584
585 &:hover {
586 color: @rcdarkblue;
587 }
568 588 }
569 589
570 .pager_curpage, .pager_dotdot,
571 .paginate_button.current, .paginate_button.disabled,
590 .paginate_button.disabled,
572 591 .disabled {
573 592 color: @grey3;
574 593 cursor: default;
594 opacity: 0.5;
595 }
596
597 .paginate_button.current, .pager_curpage {
598 background: @rcblue;
599 border-color: @rcblue;
600 color: @white;
575 601 }
576 602
577 603 .ellipsis {
578 604 display: inline-block;
579 605 text-align: left;
580 606 padding: @menupadding/4 @menupadding;
581 border: 1px solid @rcblue;
607 border: 1px solid @grey5;
582 608 border-left: 0;
583 609 float: left;
584 610 }
@@ -595,14 +621,6 b' ul#context-pages {'
595 621 font-family: @text-regular;
596 622 color: @grey1;
597 623
598 &#graph_nodes {
599 clear:both;
600 width: auto;
601 margin-left: -100px;
602 padding: 0;
603 border: none;
604 }
605
606 624 .nav-pills {
607 625 margin: 0;
608 626 }
@@ -631,19 +649,56 b' ul#context-pages {'
631 649
632 650 .main_filter_help_box {
633 651 padding: 7px 7px;
634 border-top: 1px solid @grey4;
635 border-right: 1px solid @grey4;
636 border-bottom: 1px solid @grey4;
637 652 display: inline-block;
638 653 vertical-align: top;
639 654 background: inherit;
640 655 position: absolute;
641 right: 8px;
656 right: 0;
642 657 top: 9px;
643 658 }
644 659
645 660 .main_filter_input_box {
646 661 display: inline-block;
662
663 .searchItems {
664 display:flex;
665 background: @black;
666 padding: 0px;
667 border-radius: 3px;
668 border: 1px solid @black;
669
670 a {
671 border: none !important;
672 }
673 }
674
675 .searchTag {
676 line-height: 28px;
677 padding: 0 5px;
678
679 .tag {
680 color: @grey5;
681 border-color: @grey2;
682 background: @grey1;
683 }
684 }
685
686 .searchTagFilter {
687 background-color: @black !important;
688 margin-right: 0;
689 }
690
691 .searchTagHelp {
692 background-color: @grey1 !important;
693 margin: 0;
694 }
695 .searchTagHelp:hover {
696 background-color: @grey1 !important;
697 }
698 .searchTagInput {
699 background-color: @grey1 !important;
700 margin-right: 0;
701 }
647 702 }
648 703
649 704 .main_filter_box {
@@ -651,31 +706,33 b' ul#context-pages {'
651 706 }
652 707
653 708 #main_filter_help {
654 background: @grey3;
709 background: @grey1;
655 710 border: 1px solid black;
656 711 position: absolute;
657 712 white-space: pre;
658 713 z-index: 9999;
659 714 color: @nav-grey;
660 margin: 1px 7px;
661 715 padding: 0 10px;
662 716 }
663 717
664 .main_filter_input {
665 padding: 5px;
666 min-width: 260px;
667 color: @nav-grey;
668 background: @grey3;
669 min-height: 18px;
670
718 input {
671 719
672 &:active {
673 color: @grey2 !important;
674 background: white !important;
675 }
676 &:focus {
677 color: @grey2 !important;
678 background: white !important;
720 &.main_filter_input {
721 padding: 5px 10px;
722 min-width: 340px;
723 color: @grey7;
724 background: @black;
725 min-height: 18px;
726 border: 0;
727
728 &:active {
729 color: @grey2 !important;
730 background: white !important;
731 }
732 &:focus {
733 color: @grey2 !important;
734 background: white !important;
735 }
679 736 }
680 737 }
681 738
@@ -47,7 +47,7 b''
47 47 min-height: 150px
48 48 }
49 49 }
50
50
51 51 .panel-footer {
52 52 background-color: white;
53 53 padding: .65em @panel-padding .5em;
@@ -63,10 +63,6 b''
63 63 &.user-profile {
64 64 float: left;
65 65
66 .panel-heading {
67 margin-bottom: @padding;
68 }
69
70 66 .panel-body {
71 67 &:extend(.clearfix);
72 68 }
@@ -1,11 +1,13 b''
1 1 @font-face {
2 2 font-family: 'rcicons';
3 src: url('../fonts/RCIcons/rcicons.eot?74666722');
4 src: url('../fonts/RCIcons/rcicons.eot?74666722#iefix') format('embedded-opentype'),
5 url('../fonts/RCIcons/rcicons.woff2?74666722') format('woff2'),
6 url('../fonts/RCIcons/rcicons.woff?74666722') format('woff'),
7 url('../fonts/RCIcons/rcicons.ttf?74666722') format('truetype'),
8 url('../fonts/RCIcons/rcicons.svg?74666722#rcicons') format('svg');
3
4 src: url('../fonts/RCIcons/rcicons.eot?92789106');
5 src: url('../fonts/RCIcons/rcicons.eot?92789106#iefix') format('embedded-opentype'),
6 url('../fonts/RCIcons/rcicons.woff2?92789106') format('woff2'),
7 url('../fonts/RCIcons/rcicons.woff?92789106') format('woff'),
8 url('../fonts/RCIcons/rcicons.ttf?92789106') format('truetype'),
9 url('../fonts/RCIcons/rcicons.svg?92789106#rcicons') format('svg');
10
9 11 font-weight: normal;
10 12 font-style: normal;
11 13 }
@@ -55,78 +57,164 b''
55 57 /* text-shadow: 1px 1px 1px rgba(127, 127, 127, 0.3); */
56 58 }
57 59
60 .animate-spin {
61 -moz-animation: spin 2s infinite linear;
62 -o-animation: spin 2s infinite linear;
63 -webkit-animation: spin 2s infinite linear;
64 animation: spin 2s infinite linear;
65 display: inline-block;
66 }
67 @-moz-keyframes spin {
68 0% {
69 -moz-transform: rotate(0deg);
70 -o-transform: rotate(0deg);
71 -webkit-transform: rotate(0deg);
72 transform: rotate(0deg);
73 }
74
75 100% {
76 -moz-transform: rotate(359deg);
77 -o-transform: rotate(359deg);
78 -webkit-transform: rotate(359deg);
79 transform: rotate(359deg);
80 }
81 }
82 @-webkit-keyframes spin {
83 0% {
84 -moz-transform: rotate(0deg);
85 -o-transform: rotate(0deg);
86 -webkit-transform: rotate(0deg);
87 transform: rotate(0deg);
88 }
89
90 100% {
91 -moz-transform: rotate(359deg);
92 -o-transform: rotate(359deg);
93 -webkit-transform: rotate(359deg);
94 transform: rotate(359deg);
95 }
96 }
97 @-o-keyframes spin {
98 0% {
99 -moz-transform: rotate(0deg);
100 -o-transform: rotate(0deg);
101 -webkit-transform: rotate(0deg);
102 transform: rotate(0deg);
103 }
104
105 100% {
106 -moz-transform: rotate(359deg);
107 -o-transform: rotate(359deg);
108 -webkit-transform: rotate(359deg);
109 transform: rotate(359deg);
110 }
111 }
112 @-ms-keyframes spin {
113 0% {
114 -moz-transform: rotate(0deg);
115 -o-transform: rotate(0deg);
116 -webkit-transform: rotate(0deg);
117 transform: rotate(0deg);
118 }
119
120 100% {
121 -moz-transform: rotate(359deg);
122 -o-transform: rotate(359deg);
123 -webkit-transform: rotate(359deg);
124 transform: rotate(359deg);
125 }
126 }
127 @keyframes spin {
128 0% {
129 -moz-transform: rotate(0deg);
130 -o-transform: rotate(0deg);
131 -webkit-transform: rotate(0deg);
132 transform: rotate(0deg);
133 }
134
135 100% {
136 -moz-transform: rotate(359deg);
137 -o-transform: rotate(359deg);
138 -webkit-transform: rotate(359deg);
139 transform: rotate(359deg);
140 }
141 }
142
143
144
58 145 .icon-no-margin::before {
59 146 margin: 0;
60 147
61 148 }
62 149 // -- ICON CLASSES -- //
150 // sorter = lambda s: '\n'.join(sorted(s.splitlines()))
63 151
152 .icon-delete:before { content: '\e800'; } /* '' */
153 .icon-ok:before { content: '\e801'; } /* '' */
154 .icon-comment:before { content: '\e802'; } /* '' */
64 155 .icon-bookmark:before { content: '\e803'; } /* '' */
65 156 .icon-branch:before { content: '\e804'; } /* '' */
157 .icon-tag:before { content: '\e805'; } /* '' */
66 158 .icon-lock:before { content: '\e806'; } /* '' */
67 159 .icon-unlock:before { content: '\e807'; } /* '' */
68 .icon-delete:before { content: '\e808'; } /* '' */
69 .icon-false:before { content: '\e808'; } /* '' */
70
71 .icon-ok:before { content: '\e809'; } /* '' */
72 .icon-true:before { content: '\e809'; } /* '' */
73
74 .icon-comment:before { content: '\e80a'; } /* '' */
75 .icon-comment-add:before { content: '\e816'; } /* '' */
76 .icon-comment_toggle:before { content: '\e818'; } /* '' */
77
78 .icon-feed:before { content: '\e80b'; } /* '' */
79
80 .icon-right:before { content: '\e80c'; } /* '' */
81 .icon-left:before { content: '\e80d'; } /* '' */
82
83 .icon-arrow_down:before { content: '\e80e'; } /* '' */
84 .icon-arrow_up:before { content: '\e80e'; } /* '' */
85
86 .icon-group:before { content: '\e812'; } /* '' */
87
88 .icon-fork:before { content: '\e814'; } /* '' */
89 .icon-merge:before { content: '\e814'; } /* '' */
90
91 .icon-more:before { content: '\e815'; } /* '' */
92
93 .icon-more-linked { cursor: pointer; color: @grey3 }
94 .icon-more-linked:before { content: '\e815'; } /* '' */
95
96 .icon-expand-linked { cursor: pointer; color: @grey3; font-size: 8px }
97 .icon-expand-linked:before { content: '\e80e'; } /* '' */
98
99 .icon-git-inv:before { content: '\e80f'; } /* '' */
100 .icon-hg-inv:before { content: '\e810'; } /* '' */
101 .icon-svn-inv:before { content: '\e811'; } /* '' */
102
103 .icon-git:before { content: '\e81a'; } /* '' */
104 .icon-hg:before { content: '\e81b'; } /* '' */
105 .icon-svn:before { content: '\e820'; } /* '' */
106
107 .icon-minus:before { content: '\e81c'; } /* '' */
160 .icon-feed:before { content: '\e808'; } /* '' */
161 .icon-left:before { content: '\e809'; } /* '' */
162 .icon-right:before { content: '\e80a'; } /* '' */
163 .icon-down:before { content: '\e80b'; } /* '' */
164 .icon-folder:before { content: '\e80c'; } /* '' */
165 .icon-folder-open:before { content: '\e80d'; } /* '' */
166 .icon-folder-empty:before { content: '\f114'; } /* '' */
167 .icon-folder-open-empty:before { content: '\f115'; } /* '' */
168 .icon-trash-empty:before { content: '\e80e'; } /* '' */
169 .icon-group:before { content: '\e80f'; } /* '' */
170 .icon-remove:before { content: '\e810'; } /* '' */
171 .icon-fork:before { content: '\e811'; } /* '' */
172 .icon-more:before { content: '\e812'; } /* '' */
173 .icon-search:before { content: '\e813'; } /* '' */
174 .icon-scissors:before { content: '\e814'; } /* '' */
175 .icon-download:before { content: '\e815'; } /* '' */
176 .icon-doc:before { content: '\e816'; } /* '' */
177 .icon-cog:before { content: '\e817'; } /* '' */
178 .icon-cog-alt:before { content: '\e818'; } /* '' */
179 .icon-eye:before { content: '\e819'; } /* '' */
180 .icon-eye-off:before { content: '\e81a'; } /* '' */
181 .icon-cancel-circled2:before { content: '\e81b'; } /* '' */
182 .icon-cancel-circled:before { content: '\e81c'; } /* '' */
108 183 .icon-plus:before { content: '\e81d'; } /* '' */
109 .icon-remove:before { content: '\e81e'; } /* '' */
110 .icon-remove-sign:before { content: '\e81e'; } /* '' */
111
112 .icon-rhodecode:before { content: '\e81f'; } /* '' */
113
114 .icon-tag:before { content: '\e821'; } /* '' */
115 .icon-copy:before { content: '\f0c5'; } /* '' */
116 .icon-clipboard:before { content: '\f0c5'; } /* '' */
184 .icon-plus-circled:before { content: '\e81e'; } /* '' */
185 .icon-minus-circled:before { content: '\e81f'; } /* '' */
186 .icon-minus:before { content: '\e820'; } /* '' */
187 .icon-info-circled:before { content: '\e821'; } /* '' */
188 .icon-upload:before { content: '\e822'; } /* '' */
189 .icon-home:before { content: '\e823'; } /* '' */
190 .icon-git:before { content: '\e82a'; } /* '' */
191 .icon-hg:before { content: '\e82d'; } /* '' */
192 .icon-svn:before { content: '\e82e'; } /* '' */
193 .icon-comment-add:before { content: '\e82f'; } /* '' */
194 .icon-comment-toggle:before { content: '\e830'; } /* '' */
195 .icon-rhodecode:before { content: '\e831'; } /* '' */
196 .icon-up:before { content: '\e832'; } /* '' */
197 .icon-merge:before { content: '\e833'; } /* '' */
198 .icon-docs:before { content: '\f0c5'; } /* '' */
199 .icon-menu:before { content: '\f0c9'; } /* '' */
200 .icon-paste:before { content: '\f0ea'; } /* '' */
201 .icon-doc-text:before { content: '\f0f6'; } /* '' */
202 .icon-plus-squared:before { content: '\f0fe'; } /* '' */
203 .icon-minus-squared:before { content: '\f146'; } /* '' */
204 .icon-minus-squared-alt:before { content: '\f147'; } /* '' */
205 .icon-doc-inv:before { content: '\f15b'; } /* '' */
206 .icon-doc-text-inv:before { content: '\f15c'; } /* '' */
207 .icon-plus-squared-alt:before { content: '\f196'; } /* '' */
208 .icon-file-code:before { content: '\f1c9'; } /* '' */
209 .icon-history:before { content: '\f1da'; } /* '' */
210 .icon-sliders:before { content: '\f1de'; } /* '' */
211 .icon-trash:before { content: '\f1f8'; } /* '' */
212 .icon-spin-alt:before { content: '\e834'; } /* '' */
213 .icon-spin:before { content: '\e838'; } /* '' */
117 214
118 215
119 .icon-folder:before { content: '\e813'; } /* '' */
120 .icon-folder-close:before { content: '\e813'; } /* '' */
121
122 .icon-directory:before { content: '\e800'; } /* '' */
123 .icon-directory-empty:before { content: '\f114'; } /* '' */
124 .icon-file-text:before { content: '\f0f6'; } /* '' */
125 .icon-file-text-inv:before { content: '\f15c'; } /* '' */
126 .icon-file-code:before { content: '\f1c9'; } /* '' */
127
128 // MERGED ICONS
129
216 // MERGED ICONS BASED ON CURRENT ONES
217 .icon-repo-group:before { &:extend(.icon-folder-open:before); }
130 218 .icon-repo-private:before { &:extend(.icon-lock:before); }
131 219 .icon-repo-lock:before { &:extend(.icon-lock:before); }
132 220 .icon-unlock-alt:before { &:extend(.icon-unlock:before); }
@@ -134,9 +222,20 b''
134 222 .icon-repo-public:before { &:extend(.icon-unlock:before); }
135 223 .icon-rss-sign:before { &:extend(.icon-feed:before); }
136 224 .icon-code-fork:before { &:extend(.icon-fork:before); }
225 .icon-arrow_up:before { &:extend(.icon-up:before); }
226 .icon-file:before { &:extend(.icon-file-code:before); }
227 .icon-file-text:before { &:extend(.icon-file-code:before); }
228 .icon-directory:before { &:extend(.icon-folder:before); }
229 .icon-more-linked:before { &:extend(.icon-more:before); }
230 .icon-clipboard:before { &:extend(.icon-docs:before); }
231 .icon-copy:before { &:extend(.icon-docs:before); }
232 .icon-true:before { &:extend(.icon-ok:before); }
233 .icon-false:before { &:extend(.icon-delete:before); }
234 .icon-expand-linked:before { &:extend(.icon-down:before); }
235 .icon-pr-merge-fail:before { &:extend(.icon-delete:before); }
137 236
138 237 // TRANSFORM
139 .icon-arrow_up:before {transform: rotate(180deg);}
238
140 239 .icon-merge:before {transform: rotate(180deg);}
141 240
142 241 // -- END ICON CLASSES -- //
@@ -152,6 +251,9 b''
152 251 .icon-svn-inv { color: @color1 !important; }
153 252 .icon-repo-lock { color: #FF0000; }
154 253 .icon-repo-unlock { color: #FF0000; }
254 .icon-false { color: @grey5 }
255 .icon-expand-linked { cursor: pointer; color: @grey3; font-size: 14px }
256 .icon-more-linked { cursor: pointer; color: @grey3 }
155 257
156 258 .repo-switcher-dropdown .select2-result-label {
157 259 .icon-git:before {
@@ -88,7 +88,6 b' div.readme_box pre {'
88 88 font-size: 13px !important;
89 89 overflow: visible !important;
90 90 line-height: 140% !important;
91 background-color: @grey7;
92 91 }
93 92
94 93 div.readme_box img {
@@ -156,10 +155,10 b' div.readme_box code {'
156 155 }
157 156
158 157 div.readme_box pre {
159 border: @border-thickness solid @grey5;
158 border: @border-thickness solid #CBDBEB;
160 159 overflow: auto;
161 160 padding: .5em;
162 background-color: @grey7;
161 background-color: #FCFEFF;
163 162 }
164 163
165 164 div.readme_box pre > code {
@@ -17,7 +17,7 b''
17 17 .select2-search,
18 18 .select2-search input {.box-sizing(border-box);}
19 19 .select2-container .select2-choice{display:block; line-height:1em; -webkit-touch-callout:none;-moz-user-select:none;-ms-user-select:none;user-select:none; }
20 .main .select2-container .select2-choice { background-color: white; }
20 .main .select2-container .select2-choice { background-color: white; box-shadow: @button-shadow;}
21 21 .select2-container .select2-choice abbr { display: none; width: 12px; height: 12px; position: absolute; right: 24px; top: 8px; font-size: 1px; text-decoration: none; border: 0; background: url('../images/select2.png') right top no-repeat; cursor: pointer; outline: 0; }
22 22 .select2-container.select2-allowclear .select2-choice abbr {display: inline-block;}
23 23 .select2-container .select2-choice abbr:hover { background-position: right -11px; cursor: pointer; }
@@ -92,10 +92,18 b' select.select2{height:28px;visibility:hi'
92 92 min-width: 160px;
93 93 margin: 0 @padding 0 0;
94 94 padding: 0;
95 border: @border-thickness solid @rcblue;
95 border: @border-thickness solid @grey5;
96 96 border-radius: @border-radius;
97 color: @rcblue;
97 color: @grey2;
98 98 background-color: white;
99
100 a {
101 color: @grey2;
102
103 &:hover {
104 color: @rcdarkblue;
105 }
106 }
99 107 }
100 108
101 109 .drop-menu-dropdown {
@@ -120,7 +128,7 b' select.select2{height:28px;visibility:hi'
120 128
121 129 a {
122 130 display:block;
123 padding: .9em;
131 padding: .7em;
124 132 padding-right: 2em;
125 133 position: relative;
126 134
@@ -129,7 +137,7 b' select.select2{height:28px;visibility:hi'
129 137 content: "\00A0\25BE";
130 138 right: .1em;
131 139 line-height: 1em;
132 top: 0.4em;
140 top: 0.2em;
133 141 width: 1em;
134 142 font-size: 20px;
135 143 }
@@ -157,6 +165,12 b' select.select2{height:28px;visibility:hi'
157 165 width: 100%;
158 166 margin: .5em 0;
159 167 padding: .5em;
168 border-color: @grey4;
169
170 &:focus, &:hover {
171 border-color: @rcblue;
172 box-shadow: @button-shadow;
173 }
160 174 }
161 175
162 176 .select2-no-results {
@@ -176,7 +190,13 b' select.select2{height:28px;visibility:hi'
176 190
177 191 &:hover,
178 192 &.select2-highlighted {
179 background-color: @rclightblue;
193 background-color: @grey7;
194
195 .select2-result-label {
196 &:hover {
197 color: @grey1!important;
198 }
199 }
180 200 }
181 201
182 202 &.select2-result-with-children {
@@ -189,8 +209,7 b' select.select2{height:28px;visibility:hi'
189 209 display:block;
190 210 padding: 8px;
191 211 font-family: @text-regular;
192 border-bottom: @border-thickness solid @rclightblue;
193 color: @rcblue;
212 color: @grey2;
194 213 cursor: pointer;
195 214 }
196 215 &.select2-result-with-children {
@@ -205,7 +224,7 b' select.select2{height:28px;visibility:hi'
205 224 ul.select2-result-sub li .select2-result-label {
206 225 padding-left: 16px;
207 226 font-family: @text-regular;
208 color: @rcblue;
227 color: @grey2;
209 228 cursor: pointer;
210 229 }
211 230 }
@@ -3,30 +3,33 b''
3 3 // Used for headers and file detail summary screens.
4 4
5 5 .summary {
6 float: left;
6 clear: both;
7 float: none;
7 8 position: relative;
8 9 width: 100%;
9 10 margin: 0;
10 11 padding: 0;
12 background: #FCFCFC;
13 border: 1px solid #EAEAEA;
14 border-radius: @border-radius;
15 margin-bottom: 20px;
11 16
12 17 .summary-detail-header {
13 float: left;
14 18 display: block;
15 19 width: 100%;
16 margin-bottom: @textmargin;
20 margin-bottom: 10px;
17 21 padding: 0 0 .5em 0;
18 22 border-bottom: @border-thickness solid @border-default-color;
19 23
20 24 .breadcrumbs {
21 float: left;
22 25 display: inline;
23 26 margin: 0;
24 27 padding: 0;
25 28 }
29
26 30 h4 {
27 float: left;
28 31 margin: 0 1em 0 0;
29 padding: 0;
32 padding: 10px 0 5px 20px;
30 33 line-height: 1.2em;
31 34 font-size: @basefontsize;
32 35 }
@@ -42,11 +45,11 b''
42 45 }
43 46
44 47 .summary-detail {
45 float: left;
48 float: none;
46 49 position: relative;
47 width: 73%;
48 margin: 0 3% @space 0;
49 padding: 0;
50 width: 100%;
51 margin: 0;
52 padding: 0 0 20px 0;
50 53
51 54 .file_diff_buttons {
52 55 margin-top: @space;
@@ -62,18 +65,37 b''
62 65 height: 30px;
63 66 margin: 0;
64 67 padding: 0;
68 width: 130px;
65 69 font-weight: @text-semibold-weight;
66 70 font-family: @text-semibold;
67 71 }
72 .left-clone select {
73 width: 130px;
74 margin-right: 0;
75 background-color: @grey7;
76 border-color: @grey4;
77 color: #5C5C5C;
78 border-top-right-radius: 0;
79 border-bottom-right-radius: 0;
80 }
68 81
69 82 .right-clone {
70 float: right;
71 width: 83%;
83 float: left;
84 width: ~"calc(100% - 170px)";
85
86 .clipboard-action {
87 margin-left: -30px;
88 }
72 89 }
73 90
74 91 .clone_url_input {
75 width: ~"calc(100% - 35px)";
76 padding: 5px;
92 width: ~"calc(100% - 90px)";
93 padding: 6px 30px 6px 10px;
94 height: 14px;
95 box-shadow: 0 1px 1px 0 rgba(0,0,0,0.07);
96 border-top-left-radius: 0;
97 border-bottom-left-radius: 0;
98 margin-left: -1px;
77 99 }
78 100
79 101 &.directory {
@@ -123,18 +145,32 b''
123 145 border: @border-thickness solid @border-default-color;
124 146 .border-radius(@border-radius);
125 147 }
148
149 .btn-collapse {
150 clear: both;
151 float: none;
152 background: #F7F7F7;
153 text-align: center;
154 color: #949494;
155 font-size: 11px;
156
157 &:hover {
158 background: #f1f1f1;
159 color: #2B2B2D;
160 }
161 }
126 162 }
127 163
128 164 // this is used outside of just the summary
129 165 .fieldset, // similar to form fieldset
130 166 .summary .sidebar-right-content { // these have to match
131 167 clear: both;
132 float: left;
168 float: none;
133 169 position: relative;
134 170 display:block;
135 171 width: 100%;
136 min-height: 1em;
137 margin-bottom: @textmargin;
172 min-height: 20px;
173 margin-bottom: 10px;
138 174 padding: 0;
139 175 line-height: 1.2em;
140 176
@@ -147,19 +183,28 b''
147 183 }
148 184
149 185 .summary .sidebar-right-content {
150 margin-bottom: @space;
186 margin-bottom: 0;
151 187
152 188 .rc-user {
153 189 min-width: 0;
154 190 }
191
192 li {
193 list-style: none;
194 line-height: normal;
195 }
196 }
197
198 .summary {
199 .fieldset {
200 margin-bottom: 0;
201 }
155 202 }
156 203
157 204 .fieldset {
158 205
159 206 .left-label { // similar to form legend
160 float: left;
161 207 display: block;
162 width: 25%;
163 208 margin: 0;
164 209 padding: 0;
165 210 font-weight: @text-semibold-weight;
@@ -167,16 +212,78 b''
167 212 }
168 213
169 214 .left-label-summary {
170 .left-label;
171 width: 150px;
215 padding-left: 20px;
216 margin-bottom: 5px;
217
218 p {
219 margin-bottom: 5px;
220 color: @grey1;
221 float: left;
222 width: 130px;
223
224 &.spacing {
225 margin-top: 10px;
226 }
227 }
228
229 .right-label-summary {
230 float: left;
231 margin-top: 7px;
232 width: ~"calc(100% - 160px)";
233 }
172 234 }
173
235
236 .left-label-summary-files {
237 padding-left: 45px;
238 margin-top: 5px;
239
240 p {
241 margin-bottom: 5px;
242 color: @grey1;
243 float: left;
244 width: 130px;
245
246 &.spacing {
247 margin-top: 10px;
248 }
249 }
250
251 .right-label-summary {
252 float: left;
253 margin-top: 7px;
254 }
255 }
256
257 .left-content {
258 width: ~"calc(60% - 20px)";
259 float: left;
260 margin: 15px 0 15px 20px;
261
262 .rc-user {
263 min-width: auto;
264 max-width: none;
265 min-height: auto;
266 padding-right: 5px;
267 }
268
269 .left-content-avatar {
270 width: 45px;
271 float: left;
272 margin-top: 8px;
273 }
274
275 .left-content-message {
276 float: left;
277 width: ~"calc(100% - 45px)";
278 }
279 }
280
174 281 .right-content { // similar to form fields
175 282 float: left;
176 283 display: block;
177 width: 75%;
178 margin: 0 0 0 -15%;
179 padding: 0 0 0 15%;
284 width: ~"calc(40% - 20px)";
285 text-align: right;
286 margin: 15px 20px 15px 0;
180 287
181 288 .truncate-wrap,
182 289 .truncate {
@@ -187,11 +294,49 b''
187 294 .commit-long {
188 295 overflow-x: auto;
189 296 }
297
298 .commit-info {
299 margin-top: 7px;
300 }
301
302 .summary-tag,
303 .summary-tagtag,
304 .summary-branchtag,
305 .summary-booktag,
306 .summary-metatag,
307 .summary-perm_tag {
308 background:transparent;
309 border: none;
310 box-shadow: none;
311 margin-left: 10px;
312 font-size: 13px;
313 }
314
315 .summary-tag span,
316 .summary-tag i,
317 .summary-tag a {
318 color: @grey1;
319 }
320
321 }
322 .commit {
323 color: @grey1;
324 margin-bottom: 5px;
325 white-space: pre;
190 326 }
191 327 .commit.truncate-wrap {
192 328 overflow:hidden;
193 329 text-overflow: ellipsis;
194 330 }
331 .commit-author {
332 color: @grey1;
333 }
334 .commit-date {
335 color: @grey4;
336 }
337 .fieldset-text-line {
338 line-height: 36px;
339 }
195 340 }
196 341
197 342 // expand commit message
@@ -214,19 +359,46 b''
214 359
215 360 .comments-show { display: inline; }
216 361 .comments-hide { display: none; }
217
362
218 363 &.comments-visible {
219 364 .comments-show { display: none; }
220 365 .comments-hide { display: inline; }
221 366 }
222 367 }
223
368
224 369 // Quick Start section
370
371 .empty-repo {
372 border: 1px solid #EAEAEA;
373 border-bottom: 0;
374 border-radius: @border-radius;
375 padding: 0 20px;
376 }
377
378 .empty-repo h3, .quick_start p {
379 margin-bottom: 10px;
380 }
381
382 .quick_start pre {
383 background: #FCFEFF;
384 border: 1px solid #CBDBEB;
385 box-shadow: @button-shadow;
386 padding: 10px 15px;
387 border-radius: 4px;
388 color: @grey2;
389 }
390
391 .clear-fix {
392 clear: both;
393 }
394
225 395 .quick_start {
226 float: left;
227 396 display: block;
228 397 position: relative;
229 width: 100%;
398 border: 1px solid #EAEAEA;
399 border-top: 0;
400 border-radius: @border-radius;
401 padding: 0 20px;
230 402
231 403 // adds some space to make copy and paste easier
232 404 .left-label,
@@ -235,6 +407,7 b''
235 407 }
236 408 }
237 409
410
238 411 .submodule {
239 412 .summary-detail {
240 413 width: 100%;
@@ -250,23 +423,32 b''
250 423 display: block;
251 424 width: 100%;
252 425 margin: 0;
253 padding: @space 0 10px 0;
254 border-top: @border-thickness solid @border-default-color;
426
427 .file-filename {
428 float:left;
429 padding: 10px;
430 }
255 431
256 .stats {
257 float: left;
432 .file-stats {
433 padding: 10px;
434 float:right;
258 435 }
259 .stats-filename {
260 font-size: 120%;
261 }
436
437
262 438 .stats-first-item {
263 439 padding: 0px 0px 0px 3px;
264 440 }
265 441
442 .stats-info {
443 font-size: 11px;
444 color: @grey4;
445 }
446
266 447 .buttons {
267 448 float: right;
268 449 text-align: right;
269 450 color: @grey4;
451 padding: 10px;
270 452 }
271 453
272 454 .file-container {
@@ -286,6 +468,25 b''
286 468 .repo-size {
287 469 margin-bottom: .5em;
288 470 }
289
471
290 472 }
291 473
474 .rctable.repo_summary {
475 border: 1px solid #eaeaea;
476 border-radius: 2px;
477 border-collapse: inherit;
478 border-bottom: 0;
479
480 th {
481 background: @grey7;
482 border-bottom: 0;
483 }
484
485 td {
486 border-color: #eaeaea;
487 }
488
489 td.td-status {
490 padding: 0 0 0 10px;
491 }
492 }
@@ -33,7 +33,7 b' table.dataTable {'
33 33 td {
34 34 height: auto;
35 35 max-width: 20%;
36 padding: .65em 1em .65em 0;
36 padding: .65em 0 .65em 1em;
37 37 vertical-align: middle;
38 38 border-bottom: @border-thickness solid @grey5;
39 39 white-space: normal;
@@ -103,6 +103,11 b' table.dataTable {'
103 103 }
104 104 }
105 105
106 &.td-icon {
107 min-width: 20px;
108 width: 20px;
109 }
110
106 111 &.td-hash {
107 112 min-width: 80px;
108 113 width: 200px;
@@ -113,6 +118,12 b' table.dataTable {'
113 118 }
114 119 }
115 120
121 &.td-graphbox {
122 width: 100px;
123 max-width: 100px;
124 min-width: 100px;
125 }
126
116 127 &.td-time {
117 128 width: 160px;
118 129 white-space: nowrap;
@@ -141,6 +152,11 b' table.dataTable {'
141 152 }
142 153 }
143 154
155 &.td-grid-name {
156 white-space: nowrap;
157 min-width: 300px;
158 }
159
144 160 &.td-componentname {
145 161 white-space: nowrap;
146 162 }
@@ -403,29 +419,11 b' table.trending_language_tbl {'
403 419
404 420 .trending_language {
405 421 position: relative;
406 width: 100%;
407 height: 19px;
408 422 overflow: hidden;
409 background-color: @grey6;
423 color: @text-color;
424 width: 400px;
410 425
411 span, b{
412 position: absolute;
413 display: block;
414 height: 12px;
415 margin-bottom: 0px;
416 white-space: pre;
417 padding: floor(@basefontsize/4);
418 top: 0;
419 left: 0;
420 }
421
422 span{
423 color: @text-color;
424 z-index: 0;
425 min-width: 20px;
426 }
427
428 b {
426 .lang-bar {
429 427 z-index: 1;
430 428 overflow: hidden;
431 429 background-color: @rcblue;
@@ -437,6 +435,9 b' table.trending_language_tbl {'
437 435
438 436 // Changesets
439 437 #changesets.rctable {
438 th {
439 padding: 0 1em 0.65em 0;
440 }
440 441
441 442 // td must be fixed height for graph
442 443 td {
@@ -13,15 +13,19 b''
13 13 font-size: (-1 + @basefontsize); //fit in tables
14 14 line-height: .9em;
15 15 border: none;
16 box-shadow: @button-shadow;
16 17 .border-radius(@border-radius);
17 18 font-family: @text-regular;
18 19 background-image: none;
19 20 color: @grey4;
20 .border ( @border-thickness-tags, @grey4 );
21 .border ( @border-thickness-tags, @grey5 );
21 22 white-space: nowrap;
22 23 a {
23 24 color: inherit;
24 text-decoration: underline;
25
26 &:hover {
27 color: @grey2;
28 }
25 29
26 30 i,
27 31 [class^="icon-"]:before,
@@ -29,6 +33,10 b''
29 33 text-decoration: none;
30 34 }
31 35 }
36
37 &:hover {
38 border-color: @grey4;
39 }
32 40 }
33 41
34 42 .tag0 { .border ( @border-thickness-tags, @grey4 ); color:@grey4; }
@@ -46,6 +46,13 b' h6, .h6 { font-size: 1em; font-weight'
46 46 .breadcrumbs {
47 47 font-size: @repo-title-fontsize;
48 48 margin: 0;
49 width: ~"calc(100% - 180px)";
50 float: left;
51
52 h4 {
53 font-size: @basefontsize;
54 margin-bottom: 15px;
55 }
49 56 }
50 57
51 58 .breadcrumbs_light {
@@ -156,6 +163,19 b' pre {'
156 163
157 164 // Emphasis & misc
158 165 // -------------------------
166 .discreet {
167 color: @grey4;
168 font-size: 85%;
169 font-weight: normal;
170
171 a {
172 color: @grey4;
173
174 &:hover {
175 color: @rcdarkblue;
176 }
177 }
178 }
159 179
160 180 small,
161 181 .small {
@@ -231,7 +251,8 b' mark,'
231 251 clear: both;
232 252 float: left;
233 253 width: 100%;
234 margin: @pagepadding/2 0 @pagepadding;
254 margin: @pagepadding/2 0 @pagepadding/4;
255 min-height: 25px;
235 256
236 257 .breadcrumbs {
237 258 float: left;
@@ -285,6 +306,11 b' mark,'
285 306 }
286 307
287 308 .title-content {
309
310 &.repo-title {
311 float: none
312 }
313
288 314 float: left;
289 315 margin: 0;
290 316 padding: 0;
@@ -8,13 +8,15 b''
8 8 @rchighlightblue: lighten(@rcblue, 35%);
9 9
10 10 // Secondary Colors (greyscale)
11 @grey1: #202020; //midnight
12 @grey2: #323232; //charcoal
13 @grey3: #666666; //tungsten
14 @grey4: #979797; //light grey
11 @black: #000;
12 @white: #fff;
13 @grey1: #2B2B2D; //midnight
14 @grey2: #5C5C5C; //charcoal
15 @grey3: #7E7F7F; //tungsten
16 @grey4: #949494; //light grey
15 17 @grey5: #dbd9da; //greyish
16 18 @grey6: #eeeeee; //silver
17 @grey7: #f9f9f9; //light silver
19 @grey7: #F5F5F5; //light silver
18 20
19 21 // special for navigation
20 22 @nav-grey: #CDCCCD;
@@ -102,7 +104,7 b''
102 104
103 105 // FORMS (new)
104 106 @border-thickness-inputs: 1px;
105 @input-padding: @button-padding; //needs to match button padding
107 @input-padding: .6em; //needs to match button padding
106 108 // TODO: johbo: Needed for working computation of paddings around labels etc.
107 109 // Expected to be replaced once we are done with the form refactoring.
108 110 @input-padding-px: 12px;
@@ -128,10 +130,14 b''
128 130 @fields-input-l: 720px;
129 131
130 132 // BUTTONS
131 @button-padding: .9em;
133 @button-padding: .7em;
134 @button-shadow: 0 1px 1px 0 rgba(0, 0, 0, 0.07);
135
136 // DROPDOWNS
137 @dropdown-shadow: 0 1px 2px 0 rgba(0, 0, 0, 0.07);
132 138
133 139 // DEFAULT WIDTHS
134 @wrapper-maxwidth: 1200px;
140 @wrapper-maxwidth: 1600px;
135 141 @sidebar-width: 145px;
136 142 @sidebar-all-width: @sidebar-width + 2 * @sidebarpadding;
137 143 @sidebar-small-width: 100px;
1 NO CONTENT: modified file, binary diff hidden
@@ -1,78 +1,134 b''
1 1 <?xml version="1.0" standalone="no"?>
2 2 <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
3 3 <svg xmlns="http://www.w3.org/2000/svg">
4 <metadata>Copyright (C) 2017 by original authors @ fontello.com</metadata>
4 <metadata>Copyright (C) 2019 by original authors @ fontello.com</metadata>
5 5 <defs>
6 6 <font id="rcicons" horiz-adv-x="1000" >
7 7 <font-face font-family="rcicons" font-weight="400" font-stretch="normal" units-per-em="1000" ascent="850" descent="-150" />
8 8 <missing-glyph horiz-adv-x="1000" />
9 <glyph glyph-name="directory" unicode="&#xe800;" d="M929 511v-393q0-51-37-88t-88-37h-679q-51 0-88 37t-37 88v536q0 51 37 88t88 37h179q51 0 88-37t37-88v-18h375q51 0 88-37t37-88z" horiz-adv-x="928.6" />
9 <glyph glyph-name="delete" unicode="&#xe800;" d="M515 758c-211 0-384-173-384-385 0-211 173-385 384-385s385 174 385 385c0 212-173 385-385 385z m227-416c0-15-11-27-30-27h-397c-15 0-30 12-30 27v62c0 15 11 27 30 27h397c15 0 30-12 30-27v-62z" horiz-adv-x="1000" />
10 10
11 <glyph glyph-name="bookmark" unicode="&#xe803;" d="M767-96l-234 267c-8 12-25 12-33 0l-233-267c-17-17-42-4-42 25v842c0 17 13 33 25 33h533c13 0 25-16 25-33v-838c0-29-25-46-41-29z" horiz-adv-x="1000" />
11 <glyph glyph-name="ok" unicode="&#xe801;" d="M515 735c-211 0-384-173-384-385 0-211 173-385 384-385s385 174 385 385c0 212-173 385-385 385z m239-296l-304-304c-11-12-27-12-38 0l-139 138c-11 12-11 27 0 39l42 42c12 11 27 11 39 0l58-58c11-11 27-11 38 0l219 219c12 12 27 12 39 0l42-42c15-8 15-23 4-34z" horiz-adv-x="1000" />
12
13 <glyph glyph-name="comment" unicode="&#xe802;" d="M131 65v504c0 73 58 131 131 131h507c73 0 131-58 131-131v-288c0-73-58-131-131-131h-496c-4 0-11-4-15-8l-93-92c-11-15-34-4-34 15z m131 574c-39 0-73-31-73-74v-411l46 46c4 4 7 8 15 8h519c39 0 73 31 73 73v288c0 39-30 73-73 73h-507z" horiz-adv-x="1000" />
12 14
13 <glyph glyph-name="branch" unicode="&#xe804;" d="M829 579c0 67-54 121-121 121s-125-54-125-121c0-41 21-79 59-104-17-129-125-167-192-179v287c38 21 63 59 63 105 0 66-55 120-125 120s-121-54-121-120c0-46 25-84 62-105v-458c-37-25-62-62-62-108 0-67 54-121 121-121s120 54 120 121c0 46-25 83-62 104v50c58 8 154 29 225 100 50 50 79 117 87 196 46 25 71 66 71 112z m-441 150c20 0 41-16 41-41s-16-42-41-42c-21 0-42 17-42 42s21 41 42 41z m0-750c-21 0-42 17-42 42 0 21 17 42 42 42 20 0 41-17 41-42 0-25-16-42-41-42z m320 642c21 0 42-17 42-42s-17-41-42-41c-20 0-41 16-41 41s16 42 41 42z" horiz-adv-x="1000" />
15 <glyph glyph-name="bookmark" unicode="&#xe803;" d="M780-140l-260 290c-10 10-25 10-35 0l-260-295c-20-20-45-5-45 30v930c-5 20 10 35 25 35h590c15 0 30-15 30-35v-925c0-35-30-50-45-30z" horiz-adv-x="1000" />
16
17 <glyph glyph-name="branch" unicode="&#xe804;" d="M875 600c0 76-58 134-134 134s-134-58-134-134c0-49 27-89 63-112-18-142-139-183-210-196v313c45 22 71 62 71 111 0 76-58 134-134 134s-134-58-134-134c0-49 27-94 67-116v-500c-40-22-67-67-67-116 0-76 58-134 134-134s134 58 134 134c0 49-26 94-67 116v58c63 9 166 31 246 112 58 58 89 129 98 214 40 22 67 67 67 116z m-478 161c27 0 45-18 45-45s-18-45-45-45-44 18-44 45 18 45 44 45z m0-822c-26 0-44 18-44 45s18 45 44 45 45-18 45-45-22-45-45-45z m344 706c27 0 45-18 45-45s-18-45-45-45-45 18-45 45 23 45 45 45z" horiz-adv-x="1000" />
14 18
15 <glyph glyph-name="lock" unicode="&#xe806;" d="M817 429h-50v109c0 8 0 12 0 20 0 5 0 9 0 13 0 4 0 4 0 8 0 9-4 17-4 25 0 4 0 9-5 9-4 8-4 16-8 25 0 0 0 0 0 4-4 8-8 21-12 29 0 4-5 4-5 4-4 8-8 13-12 21 0 4-4 4-4 8-4 4-9 13-13 17 0 4-4 4-4 8-8 9-12 13-21 21 0 0-4 0-4 4-8 4-12 13-21 17-4 0-4 4-8 4-8 4-13 8-21 13-4 0-4 4-8 4-9 4-17 8-29 12 0 0 0 0 0 0-9 4-21 4-30 9-4 0-4 0-8 0-4 0-8 0-8 0 0 0-4 0-4 0 0 0-5 0-5 0 0 0 0 0 0 0 0 0 0 0 0 0-4 0-8 0-8 0-4 0-4 0-8 0-4 0-4 0-9 0 0 0 0 0 0 0-4 0-8 0-8 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0-4 0-4 0 0 0-4 0-4 0-4 0-9 0-9 0-4 0-8 0-8 0-8 0-21-5-29-9 0 0 0 0 0 0-38-12-50-16-58-21-5 0-5-4-9-4-4 0-12-4-16-8-5-4-9-4-9-4-8-4-16-13-25-17 0 0-4 0-4-4-4-4-12-13-21-21 0 0-4-4-4-8-4 0-12-9-17-13 0-4-4-4-4-8-4-8-8-13-12-21 0 0-4-4-4-4-5-13-9-21-13-29 0-4 0-4-4-9-4-8-4-12-8-20 0-5 0-9-5-9 0-8-4-16-4-25 0-4 0-4 0-8 0-4 0-8 0-13 0-8 0-12 0-20v-109h-46c-16 0-29-12-29-29v-475c0-17 13-29 29-29h638c17 0 29 12 29 29v475c-4 17-17 29-33 29z m-459 109c0 66 50 125 113 137 0 0 4 0 4 0 8 0 17 0 21 4 0 0 4 0 4 0 0 0 0 0 0 0 8 0 17 0 21-4 0 0 4 0 4 0 63-12 113-71 113-137v-109h-280v109z" horiz-adv-x="1000" />
19 <glyph glyph-name="tag" unicode="&#xe805;" d="M460 788l-366 8c-18 0-31-13-31-31l13-366c0-9 4-13 9-22l464-465c14-13 31-13 45 0l352 353c14 14 14 31 0 45l-468 469c-5 4-14 9-18 9z m-103-224c0-35-31-67-67-67-35 0-67 32-67 67 0 36 32 67 67 67s67-26 67-67z" horiz-adv-x="1000" />
20
21 <glyph glyph-name="lock" unicode="&#xe806;" d="M813 426h-54v107c0 9 0 13 0 18 0 4 0 9 0 13 0 5 0 5 0 9 0 9 0 14-4 23 0 4 0 4-5 9 0 8-4 13-9 22 0 0 0 4-4 4-5 9-9 18-14 27 0 0-4 5-4 5 4 8 0 17-5 22 0 4-4 4-4 9-5 4-9 13-14 18 0 0-4 4-4 4-9 9-13 14-22 22 0 0-5 0-5 5-4 4-13 9-22 13-5 0-5 5-9 5-4 4-13 9-18 9-4 0-4 4-9 4-9 5-18 9-27 9 0 0 0 0 0 0-9 5-17 5-31 9-4 0-4 0-9 0-4 0-4 0-9 0 0 0-4 0-4 0 0 0-5 0-5 0 0 0 0 0 0 0 0 0 0 0 0 0-4 0-9 0-9 0 0 0-4 0-4 0-4 0-4 0-9 0 0 0 0 0 0 0-4 0-9 0-9 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0-4 0-4 0 0 0-5 0-5 0-4 0-4 0-9 0-4 0-4 0-9 0-9 0-22-4-31-9 0 0 0 0 0 0-22 0-36-4-45-9-4 0-4-4-8-4-5-5-9-5-18-9 0-5-5-5-5-5-9-4-18-9-22-18 0 0-5 0-5-4-9-4-13-9-22-18 0 0-4-4-4-4-5-5-9-14-14-18 0-5-4-5-4-9-9-5-14-14-14-18-4 0-4-4-4-4-5-9-9-18-13-27 0 0 0-5-5-5 0-13-4-18-4-26 0-5 0-5-5-9 0-9-4-14-4-23 0-4 0-4 0-9 0-4 0-9 0-13 0-5 0-13 0-18v-107h-49c-18 0-27-13-27-27v-464c0-18 13-27 27-27h620c18 0 27 13 27 27v464c4 18-9 27-22 27z m-451 107c0 67 49 121 111 134 0 0 0 0 5 0 9 0 13 0 22 0 0 0 5 0 5 0 0 0 0 0 0 0 8 0 13 0 22 0 0 0 0 0 4 0 63-13 112-67 112-134v-107h-281v107z" horiz-adv-x="1000" />
16 22
17 <glyph glyph-name="unlock" unicode="&#xe807;" d="M817 429h-459v109c0 66 50 125 113 137 0 0 4 0 4 0 8 0 17 0 21 4 0 0 4 0 4 0 0 0 0 0 4 0 9 0 17 0 25-4 0 0 0 0 0 0 9 0 17-4 25-8 0 0 4 0 4-4 9-5 13-9 21-13 0 0 0 0 0 0 9-4 13-8 17-17 0 0 4-4 4-4 4-4 8-8 13-16 0 0 0-5 4-5 4-8 8-12 12-20 0 0 0-5 4-5 5-8 5-12 5-20 0 0 0-5 0-5 0 0 0 0 0-4 4-12 16-25 29-25h66c17 0 30 17 30 34 0 0 0 0 0 0 0 4 0 4 0 4 0 8-5 16-5 25 0 4 0 8-4 8-4 8-4 17-8 21 4 17 4 17 4 21-4 8-8 16-12 29 0 4-5 4-5 4-4 8-8 13-12 21 0 4-4 4-4 8-4 4-9 13-13 17 0 4-4 4-4 8-8 9-12 13-21 21 0 0-4 0-4 4-8 4-12 13-21 17-12-4-16-4-16-4-9 4-13 8-21 12-4 0-4 4-9 4-8 5-16 9-29 13 0 0 0 0 0 0-8 4-21 4-29 8-4 0-4 0-8 0-9 0-17 0-25 4-4 0-9 0-9 0-8 0-16 0-29 0 0 0-4 0-4 0-8 0-21-4-29-4-8 0-13-4-21-4 0 0-4 0-4 0-113-42-188-142-188-262v-109h-50c-16 0-29-12-29-29v-475c0-17 13-29 29-29h634c16 0 29 12 29 29v475c0 17-13 29-29 29z" horiz-adv-x="1000" />
23 <glyph glyph-name="unlock" unicode="&#xe807;" d="M781 415h-385v93c0 57 43 104 96 115 0 0 0 0 4 0 8 0 12 0 19 0 0 0 4 0 4 0 0 0 0 0 4 0 8 0 16 0 23-4 0 0 0 0 0 0 8 0 12-4 19-7 0 0 4 0 4-4 4-4 12-4 16-8 0 0 0 0 0 0 4-4 11-8 15-11 0 0 4-4 4-4 4-4 8-8 11-12 0 0 0 0 4-4 4-4 8-11 12-19 0 0 0-4 0-4 4-4 4-11 4-15 0 0 0-4 0-4 0 0 0 0 0-4 4-11 11-19 23-19h57c16 0 27 11 24 27 0 0 0 0 0 0 0 0 0 4 0 4 0 7-4 11-4 19 0 4 0 4-4 8 0 15 0 19-4 27 0 0 0 3-4 3-4 8-8 16-11 23 0 0-4 4-4 4-4 8-8 12-12 16 0 4-4 4-4 7-3 4-7 12-11 16 0 0-4 4-4 4-8 7-12 11-19 19 0 0-4 0-4 4-4 4-12 7-19 11-4 0-4 4-8 4-4 4-12 8-15 8-4 0-4 4-8 4-8 3-15 7-23 7 0 0 0 0 0 0-8 4-16 4-27 8-4 0-4 0-8 0-7 0-11 0-19 4-4 0-8 0-8 0-7 0-15 0-23 0 0 0-4 0-4 0-7 0-15-4-27-4-3 0-11-4-15-4 0 0-4 0-4 0-92-27-157-115-157-215v-93h-43c-15 0-23-11-23-23v-400c0-15 12-23 23-23h535c15 0 23 12 23 23v400c4 12-8 23-23 23z" horiz-adv-x="1000" />
18 24
19 <glyph glyph-name="delete" unicode="&#xe808;" d="M500 804c-254 0-454-204-454-454 0-250 204-454 454-454s454 204 454 454c0 250-204 454-454 454z m267-491c0-17-17-34-34-34h-466c-21 0-34 13-34 34v75c0 16 17 33 34 33h466c21 0 34-13 34-33v-75z" horiz-adv-x="1000" />
25 <glyph glyph-name="feed" unicode="&#xe808;" d="M842 739h-653c-35 0-58-27-58-58v-658c0-31 27-58 58-58h657c31 0 58 27 58 58v658c-4 31-31 58-62 58z m-534-666c-39 0-73 31-73 73s30 73 73 73c38 0 73-30 73-73s-35-73-73-73z m246-11c-35 0-58 27-58 57 0 112-88 200-200 200-31 0-65 27-65 58 0 35 23 62 54 62l11 0c177 0 319-143 319-320-3-30-30-57-61-57z m196 0c-35 0-58 27-58 57 0 220-180 400-400 400-30 0-65 27-65 62 0 34 23 61 54 61l11 0c285 0 520-230 520-519 0-34-27-61-62-61z" horiz-adv-x="1000" />
26
27 <glyph glyph-name="left" unicode="&#xe809;" d="M692 773l70-69c11-12 11-27 0-39l-289-288c-11-12-11-27 0-38l296-297c12-11 12-27 0-38l-69-69c-11-12-27-12-38 0l-404 404c-12 11-12 26 0 38l396 396c11 12 27 12 38 0z" horiz-adv-x="1000" />
20 28
21 <glyph glyph-name="ok" unicode="&#xe809;" d="M500 804c-250 0-454-204-454-454 0-250 204-454 454-454s454 204 454 454c0 250-204 454-454 454z m283-346l-358-358c-12-12-33-12-46 0l-162 163c-13 12-13 33 0 45l50 50c12 13 33 13 46 0l66-66c13-13 34-13 46 0l263 262c12 13 33 13 45 0l50-50c13-16 13-37 0-46z" horiz-adv-x="1000" />
29 <glyph glyph-name="right" unicode="&#xe80a;" d="M339-65l-74 69c-11 11-11 27 0 38l289 289c11 11 11 27 0 38l-296 296c-12 12-12 27 0 39l69 69c12 12 27 12 38 0l404-404c12-11 12-27 0-38l-392-396c-12-12-31-12-38 0z" horiz-adv-x="1000" />
30
31 <glyph glyph-name="down" unicode="&#xe80b;" d="M704 454l-173-219c-8-8-23-8-27 0l-173 219c-8 11 0 31 15 31h346c12 0 20-20 12-31z" horiz-adv-x="1000" />
22 32
23 <glyph glyph-name="comment" unicode="&#xe80a;" d="M42-13v601c0 87 71 154 154 154h600c87 0 154-71 154-154v-342c0-88-71-154-154-154h-583c-9 0-13-4-17-9l-113-112c-12-17-41-4-41 16z m158 684c-46 0-87-38-87-88v-487l54 54c4 4 12 8 16 8h617c46 0 88 38 88 88v342c0 45-38 87-88 87h-600z" horiz-adv-x="1000" />
33 <glyph glyph-name="folder" unicode="&#xe80c;" d="M929 511v-393q0-51-37-88t-88-37h-679q-51 0-88 37t-37 88v536q0 51 37 88t88 37h179q51 0 88-37t37-88v-18h375q51 0 88-37t37-88z" horiz-adv-x="928.6" />
34
35 <glyph glyph-name="folder-open" unicode="&#xe80d;" d="M1049 319q0-17-18-37l-187-221q-24-28-67-48t-81-20h-607q-19 0-33 7t-15 24q0 17 17 37l188 221q24 28 67 48t80 20h607q19 0 34-7t15-24z m-192 192v-90h-464q-53 0-110-26t-92-67l-188-221-2-3q0 2-1 7t0 7v536q0 51 37 88t88 37h179q51 0 88-37t37-88v-18h303q52 0 88-37t37-88z" horiz-adv-x="1071.4" />
24 36
25 <glyph glyph-name="feed" unicode="&#xe80b;" d="M888 804h-780c-37 0-66-29-66-66v-780c0-37 29-66 66-66h780c37 0 66 29 66 66v780c0 37-29 66-66 66z m-638-787c-46 0-83 37-83 83 0 46 37 88 87 88 46 0 88-38 88-88-4-46-46-83-92-83z m292-13c-38 0-71 34-71 71 0 133-108 238-238 238-37 0-75 29-75 66 0 38 25 71 63 71l12 0c209 0 380-171 380-379 0-33-30-67-71-67z m237 0c-37 0-71 34-71 71 0 263-212 475-475 475-37 0-75 29-75 67 0 37 25 71 63 71l12 0c338 0 613-275 613-613 4-37-29-71-67-71z" horiz-adv-x="1000" />
37 <glyph glyph-name="trash-empty" unicode="&#xe80e;" d="M286 439v-321q0-8-5-13t-13-5h-36q-8 0-13 5t-5 13v321q0 8 5 13t13 5h36q8 0 13-5t5-13z m143 0v-321q0-8-5-13t-13-5h-36q-8 0-13 5t-5 13v321q0 8 5 13t13 5h36q8 0 13-5t5-13z m142 0v-321q0-8-5-13t-12-5h-36q-8 0-13 5t-5 13v321q0 8 5 13t13 5h36q7 0 12-5t5-13z m72-404v529h-500v-529q0-12 4-22t8-15 6-5h464q2 0 6 5t8 15 4 22z m-375 601h250l-27 65q-4 5-9 6h-177q-6-1-10-6z m518-18v-36q0-8-5-13t-13-5h-54v-529q0-46-26-80t-63-34h-464q-37 0-63 33t-27 79v531h-53q-8 0-13 5t-5 13v36q0 8 5 13t13 5h172l39 93q9 21 31 35t44 15h178q23 0 44-15t30-35l39-93h173q8 0 13-5t5-13z" horiz-adv-x="785.7" />
26 38
27 <glyph glyph-name="right" unicode="&#xe80c;" d="M308-96l-75 75c-12 13-12 29 0 42l309 308c12 13 12 29 0 42l-317 312c-12 13-12 30 0 42l75 75c13 13 29 13 42 0l433-433c13-13 13-29 0-42l-425-421c-8-12-29-12-42 0z" horiz-adv-x="1000" />
39 <glyph glyph-name="group" unicode="&#xe80f;" d="M962 219v-15c0-4-4-12-12-12h-161-4c-16 20-39 39-77 43-35 7-54 15-69 23 7 7 19 11 30 15 46 8 58 23 66 35 7 11 7 23 0 38-8 16-31 43-31 81 0 38 0 104 73 104h8 7c73-4 77-66 73-104 0-38-23-69-30-81-8-15-8-27 0-38 7-12 23-27 65-35 54-4 62-46 62-54 0 0 0 0 0 0z m-708-15c15 15 38 31 69 35 39 7 62 15 73 26-7 8-19 16-34 20-47 7-58 23-66 34-7 12-7 23 0 39 8 15 31 42 31 81 0 38 0 103-73 103h-8-11c-73-3-77-65-73-103 0-39 23-70 30-81 8-16 8-27 0-39-7-11-23-27-65-34-46-8-54-50-54-54 0 0 0 0 0 0v-16c0-3 4-11 12-11h161 8z m454 11c-73 12-96 35-108 54-11 20-11 39 0 62 12 23 50 69 54 131 4 61 0 165-119 169h-16-15c-119-4-123-104-119-166 4-61 38-107 54-130 11-23 11-43 0-62-12-19-35-42-108-54-73-11-85-80-85-88 0 0 0 0 0 0v-23c0-8 8-16 16-16h257 258c8 0 15 8 15 16v23c0 0 0 0 0 0-3 4-11 73-84 84z" horiz-adv-x="1000" />
40
41 <glyph glyph-name="remove" unicode="&#xe810;" d="M724 112q0-22-15-38l-76-76q-16-15-38-15t-38 15l-164 165-164-165q-16-15-38-15t-38 15l-76 76q-16 16-16 38t16 38l164 164-164 164q-16 16-16 38t16 38l76 76q16 16 38 16t38-16l164-164 164 164q16 16 38 16t38-16l76-76q15-15 15-38t-15-38l-164-164 164-164q15-15 15-38z" horiz-adv-x="785.7" />
28 42
29 <glyph glyph-name="left" unicode="&#xe80d;" d="M683 800l75-75c13-12 13-29 0-42l-308-308c-12-12-12-29 0-42l317-316c12-13 12-30 0-42l-75-75c-13-13-29-13-42 0l-433 433c-13 13-13 30 0 42l425 425c12 13 29 13 41 0z" horiz-adv-x="1000" />
43 <glyph glyph-name="fork" unicode="&#xe811;" d="M792 654c0 58-46 100-100 100-57 0-100-46-100-100 0-35 20-65 47-85-12-84-70-123-127-142-58 15-116 54-127 142 27 20 46 50 46 85 0 58-46 100-100 100s-108-42-108-100c0-39 23-73 54-89 12-107 77-188 181-226v-162c-31-19-50-50-50-88 0-58 46-101 100-101s100 47 100 101c0 38-19 69-50 88v162c104 38 169 119 181 226 30 20 53 50 53 89z m-465 35c19 0 35-16 35-35s-16-31-35-31-35 12-35 31 16 35 35 35z m181-635c-19 0-35 15-35 35s16 34 35 34c19 0 34-15 34-34s-15-35-34-35z m184 635c20 0 35-16 35-35s-15-31-35-31-34 16-34 35 15 31 34 31z" horiz-adv-x="1000" />
44
45 <glyph glyph-name="more" unicode="&#xe812;" d="M546 435h-100c-15 0-27-12-27-27v-100c0-16 12-27 27-27h100c16 0 27 11 27 27v100c0 15-11 27-27 27z m0 307h-100c-15 0-27-11-27-27v-100c0-15 12-26 27-26h100c16 0 27 11 27 26v100c0 16-11 27-27 27z m0-615h-100c-15 0-27-12-27-27v-100c0-15 12-27 27-27h100c16 0 27 12 27 27v100c0 15-11 27-27 27z" horiz-adv-x="1000" />
30 46
31 <glyph glyph-name="arrow_down" unicode="&#xe80e;" d="M950 542l-412-521c-17-21-50-21-67 0l-417 521c-21 25-4 71 34 71h829c37 0 58-46 33-71z" horiz-adv-x="1000" />
47 <glyph glyph-name="search" unicode="&#xe813;" d="M643 386q0 103-73 176t-177 74-177-74-73-176 73-177 177-73 177 73 73 177z m286-465q0-29-22-50t-50-21q-30 0-50 21l-191 191q-100-69-223-69-80 0-153 31t-125 84-84 125-31 153 31 152 84 126 125 84 153 31 153-31 125-84 84-126 31-152q0-123-69-223l191-191q21-21 21-51z" horiz-adv-x="928.6" />
48
49 <glyph glyph-name="scissors" unicode="&#xe814;" d="M536 350q14 0 25-11t10-25-10-25-25-10-25 10-11 25 11 25 25 11z m167-36l283-222q16-11 14-31-3-20-19-28l-72-36q-7-4-16-4-10 0-17 4l-385 216-62-36q-4-3-7-3 8-28 6-54-4-43-31-83t-74-69q-74-47-154-47-76 0-124 44-51 47-44 116 4 42 31 82t73 69q74 47 155 47 46 0 84-18 5 8 13 13l68 40-68 41q-8 5-13 12-38-17-84-17-81 0-155 47-46 30-73 69t-31 82q-3 33 8 63t36 52q47 44 124 44 80 0 154-47 46-29 74-68t31-83q2-27-6-54 3-1 7-3l62-37 385 216q7 5 17 5 9 0 16-4l72-36q16-9 19-28 2-20-14-32z m-380 145q26 24 12 61t-59 65q-52 33-107 33-42 0-63-20-26-24-12-60t59-66q51-33 107-33 41 0 63 20z m-47-415q45 28 59 65t-12 60q-22 20-63 20-56 0-107-33-45-28-59-65t12-60q21-20 63-20 55 0 107 33z m99 342l54-33v7q0 20 18 31l8 4-44 26-15-14q-1-2-5-6t-7-7q-1-1-2-2t-2-1z m125-125l54-18 410 321-71 36-429-240v-64l-89-53 5-5q1-1 4-3 2-2 6-7t6-6l15-15z m393-232l71 35-290 228-99-77q-1-2-7-4z" horiz-adv-x="1000" />
32 50
33 <glyph glyph-name="git" unicode="&#xe80f;" d="M896 808h-792c-33 0-62-29-62-62v-792c0-33 29-62 62-62h792c33 0 62 29 62 62v792c0 33-29 62-62 62z m-4-850h-788v788h788v-788z m-667 338c-4 12-8 25-8 42 0 12 0 25 4 37 4 13 8 21 12 33s13 21 21 30 17 16 25 20c13 0 21 5 34 9 8 4 20 4 33 4 8 0 21 0 29-4 8 0 17-4 21-9 8-4 12-8 17-12 4-4 8-8 12-13l-17-20c-4-5-4-5-8-9-4 0-8 0-12 4-5 5-9 5-13 9-4 0-8 4-8 4-4 0-9 4-13 4-4 0-8 0-12 0-9 0-21-4-29-8-9-4-17-13-21-17-4-8-13-17-13-29-4-13-4-25-4-38 0-8 0-20 4-29 4-8 4-16 13-21 4-4 8-8 16-12 9-4 13-4 21-4 9 0 13 0 17 0 4 0 8 4 17 4l4 37h-25c-4 0-4 0-9 5s0 8 0 12l5 29h79l-13-100c-4-4-12-8-16-12-9-4-13-4-21-9-9 0-13-4-21-4-8 0-17 0-25 0-13 0-29 4-42 9-12 4-21 12-29 20-12 13-21 21-25 38z m300-63h-54l29 234h54l-29-234z m146 192h-58l4 42h171l-5-42h-58l-25-192h-54l25 192z" horiz-adv-x="1000" />
51 <glyph glyph-name="download" unicode="&#xe815;" d="M714 100q0 15-10 25t-25 11-25-11-11-25 11-25 25-11 25 11 10 25z m143 0q0 15-10 25t-26 11-25-11-10-25 10-25 25-11 26 11 10 25z m72 125v-179q0-22-16-37t-38-16h-821q-23 0-38 16t-16 37v179q0 22 16 38t38 16h259l75-76q33-32 76-32t76 32l76 76h259q22 0 38-16t16-38z m-182 318q10-23-8-39l-250-250q-10-11-25-11t-25 11l-250 250q-17 16-8 39 10 21 33 21h143v250q0 15 11 25t25 11h143q14 0 25-11t10-25v-250h143q24 0 33-21z" horiz-adv-x="928.6" />
52
53 <glyph glyph-name="doc" unicode="&#xe816;" d="M819 638q16-16 27-42t11-50v-642q0-23-15-38t-38-16h-750q-23 0-38 16t-16 38v892q0 23 16 38t38 16h500q22 0 49-11t42-27z m-248 136v-210h210q-5 17-12 23l-175 175q-6 7-23 12z m215-853v572h-232q-23 0-38 16t-16 37v233h-429v-858h715z" horiz-adv-x="857.1" />
34 54
35 <glyph glyph-name="hg" unicode="&#xe810;" d="M896 808h-792c-33 0-62-29-62-62v-792c0-33 29-62 62-62h792c33 0 62 29 62 62v792c-4 33-29 62-62 62z m-4-850h-788v788h788v-788z m-571 275h-54l29 234h54l-12-100h83l12 100h55l-30-234h-54l13 100h-84l-12-100z m217 63c-5 12-9 25-9 42 0 12 0 25 4 37 5 13 9 21 13 33 4 9 12 21 21 25s16 17 25 21c8 4 21 9 29 13 12 4 21 4 33 4 9 0 21 0 29-4s17-4 21-9c9-4 13-8 17-12 4-4 8-8 12-13l-16-20c-4-5-4-5-9-9-4 0-8 0-12 4-4 5-8 5-13 9-4 0-8 4-8 4-4 0-8 4-12 4-5 0-9 0-13 0-8 0-21-4-29-8-8-4-17-13-21-17s-12-17-12-29c-5-13-5-25-5-38 0-8 0-20 5-29 4-8 4-16 12-21 4-4 8-8 17-12 8-4 12-4 21-4 8 0 12 0 16 0 4 0 9 4 17 4l4 37h-21c-4 0-4 0-8 5s-4 4 0 8l4 29h79l-12-100c-4-4-13-8-17-12-8-5-12-5-21-9-8 0-12-4-21-4-8 0-16 0-25 0-12 0-29 4-41 8-13 5-21 13-29 21-13 17-21 29-25 42z" horiz-adv-x="1000" />
55 <glyph glyph-name="cog" unicode="&#xe817;" d="M571 350q0 59-41 101t-101 42-101-42-42-101 42-101 101-42 101 42 41 101z m286 61v-124q0-7-4-13t-11-7l-104-16q-10-30-21-51 19-27 59-77 6-6 6-13t-5-13q-15-21-55-61t-53-39q-7 0-14 5l-77 60q-25-13-51-21-9-76-16-104-4-16-20-16h-124q-8 0-14 5t-6 12l-16 103q-27 9-50 21l-79-60q-6-5-14-5-8 0-14 6-70 64-92 94-4 5-4 13 0 6 5 12 8 12 28 37t30 40q-15 28-23 55l-102 15q-7 1-11 7t-5 13v124q0 7 5 13t10 7l104 16q8 25 22 51-23 32-60 77-6 7-6 14 0 5 5 12 15 20 55 60t53 40q7 0 15-5l77-60q24 13 50 21 9 76 17 104 3 16 20 16h124q7 0 13-5t7-12l15-103q28-9 51-20l79 59q5 5 13 5 7 0 14-5 72-67 92-95 4-5 4-12 0-7-4-13-9-12-29-37t-30-40q15-28 23-54l102-16q7-1 12-7t4-13z" horiz-adv-x="857.1" />
56
57 <glyph glyph-name="cog-alt" unicode="&#xe818;" d="M500 350q0 59-42 101t-101 42-101-42-42-101 42-101 101-42 101 42 42 101z m429-286q0 29-22 51t-50 21-50-21-21-51q0-29 21-50t50-21 51 21 21 50z m0 572q0 29-22 50t-50 21-50-21-21-50q0-30 21-51t50-21 51 21 21 51z m-215-235v-103q0-6-4-11t-8-6l-87-14q-6-19-18-42 19-27 50-64 4-6 4-11 0-7-4-11-12-17-46-50t-43-33q-7 0-12 4l-64 50q-21-11-43-17-6-60-13-87-4-13-17-13h-104q-6 0-11 4t-5 10l-13 85q-19 6-42 18l-66-50q-4-4-11-4-6 0-12 4-80 75-80 90 0 5 4 10 5 8 23 30t26 34q-13 24-20 46l-85 13q-5 1-9 5t-4 11v104q0 5 4 10t9 6l86 14q7 19 18 42-19 27-50 64-4 6-4 11 0 7 4 12 12 16 46 49t44 33q6 0 12-4l64-50q19 10 43 18 6 60 13 86 3 13 16 13h104q6 0 11-4t6-10l13-85q19-6 42-17l65 49q5 4 12 4 6 0 11-4 81-75 81-90 0-4-4-10-7-9-24-30t-25-34q13-27 19-46l85-12q6-2 9-6t4-11z m357-298v-78q0-9-83-17-6-15-16-29 28-63 28-77 0-2-2-4-68-40-69-40-5 0-26 27t-29 37q-11-1-17-1t-17 1q-7-11-29-37t-25-27q-1 0-69 40-3 2-3 4 0 14 29 77-10 14-17 29-83 8-83 17v78q0 9 83 18 7 16 17 29-29 63-29 77 0 2 3 4 2 1 19 11t33 19 17 9q4 0 25-26t29-38q12 1 17 1t17-1q28 40 51 63l4 1q2 0 69-39 2-2 2-4 0-14-28-77 9-13 16-29 83-9 83-18z m0 572v-78q0-9-83-18-6-15-16-29 28-63 28-77 0-2-2-4-68-39-69-39-5 0-26 26t-29 38q-11-1-17-1t-17 1q-7-12-29-38t-25-26q-1 0-69 39-3 2-3 4 0 14 29 77-10 14-17 29-83 9-83 18v78q0 9 83 17 7 16 17 29-29 63-29 77 0 2 3 4 2 1 19 11t33 19 17 9q4 0 25-26t29-37q12 1 17 1t17-1q28 39 51 62l4 1q2 0 69-39 2-2 2-4 0-14-28-77 9-13 16-29 83-8 83-17z" horiz-adv-x="1071.4" />
36 58
37 <glyph glyph-name="svn" unicode="&#xe811;" d="M896 808h-792c-33 0-62-29-62-62v-796c0-29 29-58 62-58h796c33 0 63 29 63 62v792c-5 33-34 62-67 62z m0-854h-792v792h788v-792z m-717 296c-4 4-8 8-12 13l21 25c0 0 4 4 4 4 4 0 4 0 8 0 4 0 4 0 8-4 5 0 5-5 9-9 4-4 8-4 12-8 4 0 9-4 17-4 8 0 17 4 21 8 4 4 8 13 8 25 0 4 0 8-4 13-4 4-4 4-8 8-5 4-9 4-13 4-4 0-8 4-17 4-4 0-12 4-16 9-4 4-9 8-13 12-4 4-8 8-8 17-4 4-4 12-4 21 0 12 0 20 4 29 4 8 8 16 17 25 8 8 16 12 25 16 12 9 25 13 37 13 8 0 13 0 21 0 8 0 12-4 17-4 4-4 12-4 16-9 4-8 9-12 9-16l-17-21c0-4-4-4-4-4 0 0-4 0-9 0-4 0-4 0-8 4-4 0-4 4-8 4-4 0-9 4-13 4-4 0-8 4-12 4-4 0-9 0-13 0-4 0-8-4-8-4-4-4-4-4-4-8 0-4 0-8 0-13 0-4 0-8 4-12 4-4 4-4 8-8 4-5 9-5 13-5 4 0 8-4 16-4 5-4 13-4 17-8 4-4 8-8 13-13s8-8 8-16c4-4 4-13 4-21 0-13 0-25-4-33-4-13-8-21-17-30-8-8-16-12-29-16-12-4-25-9-37-9-9 0-13 0-21 5s-13 4-21 8c-4-4-13 0-17 4z m250-17l-54 234h42c4 0 8 0 12-4 4-5 4-5 4-9l25-129c0-4 5-12 5-17 0-8 4-12 4-20 4 8 4 12 8 20 4 9 4 13 8 17l55 129c0 0 0 4 4 4 0 0 4 5 4 5 0 0 4 0 4 4 0 0 4 0 4 0h42l-117-238h-50z m221 0h-46l29 238h30c4 0 4 0 4 0 0 0 4 0 4 0 0 0 4 0 4-4 0 0 0-4 4-4l84-146c0 4 0 8 0 12 0 4 0 9 0 9l16 133h46l-29-238h-29c-4 0-9 0-9 0-4 0-4 5-8 9l-83 146c0-5 0-5 0-9 0-4 0-4 0-8l-17-138z" horiz-adv-x="1000" />
59 <glyph glyph-name="eye" unicode="&#xe819;" d="M929 314q-85 132-213 197 34-58 34-125 0-103-73-177t-177-73-177 73-73 177q0 67 34 125-128-65-213-197 75-114 187-182t242-68 243 68 186 182z m-402 215q0 11-8 19t-19 7q-70 0-120-50t-50-119q0-11 8-19t19-8 19 8 8 19q0 48 34 82t82 34q11 0 19 8t8 19z m473-215q0-19-11-38-78-129-210-206t-279-77-279 77-210 206q-11 19-11 38t11 39q78 128 210 205t279 78 279-78 210-205q11-20 11-39z" horiz-adv-x="1000" />
60
61 <glyph glyph-name="eye-off" unicode="&#xe81a;" d="M310 105l43 79q-48 35-76 88t-27 114q0 67 34 125-128-65-213-197 94-144 239-209z m217 424q0 11-8 19t-19 7q-70 0-120-50t-50-119q0-11 8-19t19-8 19 8 8 19q0 48 34 82t82 34q11 0 19 8t8 19z m202 106q0-4 0-5-59-105-176-316t-176-316l-28-50q-5-9-15-9-7 0-75 39-9 6-9 16 0 7 25 49-80 36-147 96t-117 137q-11 17-11 38t11 39q86 131 212 207t277 76q50 0 100-10l31 54q5 9 15 9 3 0 10-3t18-9 18-10 18-10 10-7q9-5 9-15z m21-249q0-78-44-142t-117-91l157 280q4-25 4-47z m250-72q0-19-11-38-22-36-61-81-84-96-194-149t-234-53l41 74q119 10 219 76t169 171q-65 100-158 164l35 63q53-36 102-85t81-103q11-19 11-39z" horiz-adv-x="1000" />
38 62
39 <glyph glyph-name="group" unicode="&#xe812;" d="M958 221v-17c0-4-4-8-8-8h-167-4c-16 21-41 37-79 46-37 4-58 16-71 25 9 8 17 12 34 16 45 9 62 21 66 38s9 25 0 37c-8 13-33 46-33 84 0 41 0 104 75 108h8 13c75-4 79-71 75-108 0-42-25-71-34-84-8-16-8-25 0-37s21-29 67-38c54-12 58-58 58-62 0 0 0 0 0 0z m-725-17c17 17 38 34 71 38 42 8 63 16 75 25-8 8-21 16-37 21-46 8-63 20-67 37-8 13-8 25 0 38 8 12 33 45 33 83 0 42 0 104-75 108h-12-8c-75-4-80-71-80-108 0-42 25-71 34-83 8-17 8-25 0-38-9-12-21-29-67-37-50-9-54-50-54-59 0 0 0 0 0 0v-16c0-5 4-9 8-9h167 12z m463 13c-75 12-96 37-108 58-13 21-13 42 0 63 12 25 50 70 54 133 4 62 0 167-121 175h-21-17c-116-4-120-113-120-175 4-63 41-113 54-133 12-25 12-42 0-63-13-21-38-46-109-58-75-13-87-84-87-92 0 0 0 0 0 0v-25c0-8 8-17 17-17h262 267c8 0 16 9 16 17v25c0 0 0 0 0 0 0 8-8 79-87 92z" horiz-adv-x="1000" />
63 <glyph glyph-name="cancel-circled2" unicode="&#xe81b;" d="M612 248l-81-82q-6-5-13-5t-13 5l-76 77-77-77q-5-5-13-5t-12 5l-82 82q-6 6-6 13t6 13l76 76-76 77q-6 5-6 12t6 13l82 82q5 5 12 5t13-5l77-77 76 77q6 5 13 5t13-5l81-82q6-5 6-13t-6-12l-76-77 76-76q6-6 6-13t-6-13z m120 102q0 83-41 152t-110 111-152 41-153-41-110-111-41-152 41-152 110-111 153-41 152 41 110 111 41 152z m125 0q0-117-57-215t-156-156-215-58-216 58-155 156-58 215 58 215 155 156 216 58 215-58 156-156 57-215z" horiz-adv-x="857.1" />
64
65 <glyph glyph-name="cancel-circled" unicode="&#xe81c;" d="M641 224q0 14-10 25l-101 101 101 101q10 11 10 25 0 15-10 26l-51 50q-10 11-25 11-15 0-25-11l-101-101-101 101q-11 11-25 11-16 0-26-11l-50-50q-11-11-11-26 0-14 11-25l101-101-101-101q-11-11-11-25 0-15 11-26l50-50q10-11 26-11 14 0 25 11l101 101 101-101q10-11 25-11 15 0 25 11l51 50q10 11 10 26z m216 126q0-117-57-215t-156-156-215-58-216 58-155 156-58 215 58 215 155 156 216 58 215-58 156-156 57-215z" horiz-adv-x="857.1" />
40 66
41 <glyph glyph-name="folder" unicode="&#xe813;" d="M742 17h-659c-12 0-25 8-33 16-8 13-8 25 0 38l179 342c4 12 17 20 34 20h658c12 0 25-8 33-16 9-13 9-25 0-38l-179-341c-8-13-21-21-33-21z m-596 75h575l142 266h-580l-137-266z m-29-38h-75v550c0 21 16 38 37 38h246c8 0 21-4 25-13l54-54h325c21 0 38-17 38-37v-105h-75v67h-300c-9 0-17 4-25 8l-59 59h-191v-513z" horiz-adv-x="1000" />
67 <glyph glyph-name="plus" unicode="&#xe81d;" d="M786 439v-107q0-22-16-38t-38-15h-232v-233q0-22-16-37t-38-16h-107q-22 0-38 16t-15 37v233h-232q-23 0-38 15t-16 38v107q0 23 16 38t38 16h232v232q0 22 15 38t38 16h107q23 0 38-16t16-38v-232h232q23 0 38-16t16-38z" horiz-adv-x="785.7" />
42 68
43 <glyph glyph-name="fork" unicode="&#xe814;" d="M838 688c0 66-55 120-121 120-67 0-121-54-121-120 0-42 21-80 54-100-12-100-83-146-150-167-71 21-137 67-150 167 33 20 54 58 54 100 0 66-54 120-121 120s-120-54-120-120c0-46 29-88 66-109 13-129 88-225 213-271v-191c-38-21-63-59-63-100 0-67 54-121 121-121s121 54 121 121c0 46-25 83-58 104v192c120 45 200 137 212 270 33 17 63 59 63 105z m-555 37c21 0 42-17 42-42s-17-41-42-41-41 16-41 41 21 42 41 42z m217-750c-21 0-42 17-42 42 0 21 17 41 42 41s42-16 42-41c0-25-21-42-42-42z m217 750c21 0 41-17 41-42s-16-41-41-41-42 16-42 41 21 42 42 42z" horiz-adv-x="1000" />
69 <glyph glyph-name="plus-circled" unicode="&#xe81e;" d="M679 314v72q0 14-11 25t-25 10h-143v143q0 15-11 25t-25 11h-71q-15 0-25-11t-11-25v-143h-143q-14 0-25-10t-10-25v-72q0-14 10-25t25-10h143v-143q0-15 11-25t25-11h71q15 0 25 11t11 25v143h143q14 0 25 10t11 25z m178 36q0-117-57-215t-156-156-215-58-216 58-155 156-58 215 58 215 155 156 216 58 215-58 156-156 57-215z" horiz-adv-x="857.1" />
70
71 <glyph glyph-name="minus-circled" unicode="&#xe81f;" d="M679 314v72q0 14-11 25t-25 10h-429q-14 0-25-10t-10-25v-72q0-14 10-25t25-10h429q14 0 25 10t11 25z m178 36q0-117-57-215t-156-156-215-58-216 58-155 156-58 215 58 215 155 156 216 58 215-58 156-156 57-215z" horiz-adv-x="857.1" />
44 72
45 <glyph glyph-name="more" unicode="&#xe815;" d="M592 408v-120c0-17-13-34-34-34h-120c-17 0-34 13-34 34v120c0 17 13 34 34 34h120c21 0 34-17 34-34z m-34 400h-120c-17 0-34-12-34-33v-121c0-16 13-33 34-33h120c17 0 34 12 34 33v121c0 21-13 33-34 33z m0-733h-120c-17 0-34-12-34-33v-121c0-17 13-34 34-34h120c17 0 34 13 34 34v121c0 16-13 33-34 33z" horiz-adv-x="1000" />
73 <glyph glyph-name="minus" unicode="&#xe820;" d="M786 439v-107q0-22-16-38t-38-15h-678q-23 0-38 15t-16 38v107q0 23 16 38t38 16h678q23 0 38-16t16-38z" horiz-adv-x="785.7" />
74
75 <glyph glyph-name="info-circled" unicode="&#xe821;" d="M571 82v89q0 8-5 13t-12 5h-54v286q0 8-5 13t-13 5h-178q-8 0-13-5t-5-13v-89q0-8 5-13t13-5h53v-179h-53q-8 0-13-5t-5-13v-89q0-8 5-13t13-5h250q7 0 12 5t5 13z m-71 500v89q0 8-5 13t-13 5h-107q-8 0-13-5t-5-13v-89q0-8 5-13t13-5h107q8 0 13 5t5 13z m357-232q0-117-57-215t-156-156-215-58-216 58-155 156-58 215 58 215 155 156 216 58 215-58 156-156 57-215z" horiz-adv-x="857.1" />
46 76
47 <glyph glyph-name="comment-add" unicode="&#xe816;" d="M48-12v593c0 86 69 155 154 155h596c85 0 154-69 154-155v-338c0-86-69-155-154-155h-584c-7 0-12-2-16-7l-110-110c-14-14-40-4-40 17z m154 679c-47 0-85-38-85-86v-486l52 53c5 4 10 7 17 7h612c47 0 85 38 85 86v340c0 48-38 86-85 86h-596z m479-284l0 48c0 5-5 10-10 10l-114 0c-5 0-9 4-9 9v114c0 5-5 10-10 10h-47c-5 0-10-5-10-10v-114c0-5-5-9-10-9h-114c-5 0-9-5-9-10v-48c0-4 4-9 9-9h114c5 0 10-5 10-10l0-114c0-5 5-9 10-9l47 0c5 0 10 4 10 9v114c0 5 4 10 9 10h114c5-3 10 2 10 9z" horiz-adv-x="1000" />
77 <glyph glyph-name="upload" unicode="&#xe822;" d="M714 29q0 14-10 25t-25 10-25-10-11-25 11-25 25-11 25 11 10 25z m143 0q0 14-10 25t-26 10-25-10-10-25 10-25 25-11 26 11 10 25z m72 125v-179q0-22-16-38t-38-16h-821q-23 0-38 16t-16 38v179q0 22 16 38t38 15h238q12-31 39-51t62-20h143q34 0 61 20t40 51h238q22 0 38-15t16-38z m-182 361q-9-22-33-22h-143v-250q0-15-10-25t-25-11h-143q-15 0-25 11t-11 25v250h-143q-23 0-33 22-9 22 8 39l250 250q10 10 25 10t25-10l250-250q18-17 8-39z" horiz-adv-x="928.6" />
78
79 <glyph glyph-name="home" unicode="&#xe823;" d="M888 336q16-16 11-27t-27-11l-84 0 0-310q0-14-1-21t-8-13-23-6l-204 0 0 310-204 0 0-310-194 0q-28 0-35 10t-7 30l0 310-84 0q-22 0-27 11t11 27l400 402q16 16 38 16t38-16z" horiz-adv-x="900" />
48 80
49 <glyph glyph-name="comment_toggle" unicode="&#xe818;" d="M798 736h-596c-85 0-154-69-154-155v-593c0-19 22-29 36-20 2 1 5 3 7 5l109 109c2 2 5 4 8 5 2 1 4 1 6 1h584c85 0 154 69 154 155v338c0 86-69 155-154 155z m-680-639v484c0 47 38 85 86 85h476c-86-84-504-511-509-515l-53-54z" horiz-adv-x="1000" />
81 <glyph glyph-name="git" unicode="&#xe82a;" d="M929 844h-858c-36 0-65-30-65-65v-857c0-36 30-65 65-65h857c36 0 65 30 65 65v857c1 35-29 65-64 65z m-729-549c4-11 9-20 14-27 6-8 14-14 22-18 9-4 19-6 29-6 9 0 16 1 24 2 7 2 14 4 20 7l6 51h-27c-4 0-8 1-10 4-2 1-3 5-3 7l5 39h105l-16-131c-8-7-16-12-25-15-9-4-18-8-28-10-10-3-18-5-30-7-10-1-21-2-33-2-20 0-38 4-54 11-16 8-30 18-41 30-12 13-20 28-27 45-6 18-10 36-10 56 0 18 3 34 7 50 3 17 10 30 17 44 8 14 16 25 26 36 10 12 22 20 34 28 13 7 26 14 41 17 15 4 30 7 47 7 13 0 25-2 36-4 11-3 21-6 29-10 8-4 16-9 22-14 6-5 13-11 18-16l-20-31c-4-5-9-8-14-9-5-1-10 0-16 4-5 3-10 6-14 8-5 3-9 5-14 7-5 1-10 2-15 3-5 2-11 2-17 2-14 0-27-3-38-9-11-6-21-14-29-25-8-10-15-24-18-38-5-15-7-31-7-48-1-14 2-27 4-38z m336-102h-71l39 315h71l-39-315z m343 258h-80l-33-258h-70l32 258h-80l7 57h231l-7-57z" horiz-adv-x="1000" />
50 82
51 <glyph glyph-name="git-inv" unicode="&#xe81a;" d="M929 844h-858c-36 0-65-30-65-65v-857c0-36 30-65 65-65h857c36 0 65 30 65 65v857c1 35-29 65-64 65z m-729-549c4-11 9-20 14-27 6-8 14-14 22-18 9-4 19-6 29-6 9 0 16 1 24 2 7 2 14 4 20 7l6 51h-27c-4 0-8 1-10 4-2 1-3 5-3 7l5 39h105l-16-131c-8-7-16-12-25-15-9-4-18-8-28-10-10-3-18-5-30-7-10-1-21-2-33-2-20 0-38 4-54 11-16 8-30 18-41 30-12 13-20 28-27 45-6 18-10 36-10 56 0 18 3 34 7 50 3 17 10 30 17 44 8 14 16 25 26 36 10 12 22 20 34 28 13 7 26 14 41 17 15 4 30 7 47 7 13 0 25-2 36-4 11-3 21-6 29-10 8-4 16-9 22-14 6-5 13-11 18-16l-20-31c-4-5-9-8-14-9-5-1-10 0-16 4-5 3-10 6-14 8-5 3-9 5-14 7-5 1-10 2-15 3-5 2-11 2-17 2-14 0-27-3-38-9-11-6-21-14-29-25-8-10-15-24-18-38-5-15-7-31-7-48-1-14 2-27 4-38z m336-102h-71l39 315h71l-39-315z m343 258h-80l-33-258h-70l32 258h-80l7 57h231l-7-57z" horiz-adv-x="1000" />
83 <glyph glyph-name="hg" unicode="&#xe82d;" d="M927 841h-853c-36 0-65-29-65-65v-853c0-36 29-65 65-65h853c36 0 65 29 65 65v853c0 36-29 65-65 65z m-483-648h-70l16 133h-113l-17-133h-70l39 313h70l-16-132h113l16 132h71l-39-313z m177 101c3-11 8-20 14-27 7-8 14-14 23-18 8-4 18-6 28-6 9 0 16 1 23 3 7 1 14 3 20 6l6 51h-27c-4 0-7 1-9 3-3 3-3 6-3 9l5 39h104l-16-131c-8-6-16-11-25-15-9-5-18-8-27-11-9-2-19-4-30-6-10-1-21-2-33-2-19 0-37 4-53 11-16 7-30 17-41 29-11 13-20 28-26 45-7 17-10 35-10 55 0 17 2 34 6 50 4 15 10 30 17 43 7 14 16 26 26 36 10 11 22 20 34 28 13 7 27 13 41 17 14 4 30 7 46 7 13 0 25-2 36-4 11-3 20-6 29-10 8-4 16-9 23-14 7-5 13-11 18-17l-23-28c-4-5-8-8-13-9-5-1-11 0-16 3-5 4-10 7-14 9-5 3-9 5-14 6-4 2-9 3-14 4-5 1-11 1-17 1-14 0-27-3-38-8-11-6-21-14-29-25-8-10-15-23-19-38-5-15-7-31-7-49 0-13 2-26 5-37z" horiz-adv-x="1000" />
84
85 <glyph glyph-name="svn" unicode="&#xe82e;" d="M933 841h-852c-36 0-65-29-65-65v-853c0-36 29-65 65-65h852c36 0 66 29 66 65v853c0 36-30 65-66 65z m-765-438c3-4 7-7 13-10 5-3 11-6 18-8 7-3 14-5 21-8 7-3 14-6 21-10 7-4 13-9 18-14 5-6 10-13 13-20 3-8 5-18 5-29 0-16-3-30-8-44-6-14-14-26-24-37-10-10-22-18-37-24-15-7-31-10-49-10-9 0-18 1-27 3s-18 5-27 9c-8 4-16 8-23 13-7 5-13 10-18 17l25 32c2 3 4 5 7 6 3 2 6 3 9 3 4 0 8-2 12-4 3-3 8-6 12-10 5-3 10-6 16-9 6-3 14-4 23-4 13 0 23 3 30 10 7 7 10 18 10 32 0 6-1 12-4 16-4 4-8 7-13 10-5 3-11 6-18 8-7 2-14 5-21 7-7 3-14 6-21 9-6 4-12 8-18 14-5 6-9 13-12 21-3 8-5 18-5 30 0 14 3 28 8 40 5 13 12 25 22 35 10 9 22 17 36 23 14 6 29 9 47 9 9 0 17-1 26-3s16-4 23-8c7-3 14-7 20-11 6-5 11-10 15-15l-21-29c-2-3-5-6-7-7-3-2-6-3-9-3-3 0-7 1-10 3-3 3-7 5-11 8-4 2-9 4-14 7-5 2-12 3-19 3-6 0-12-1-17-3-5-2-9-4-12-8-4-3-6-7-8-11-1-5-2-10-2-15 0-5 2-10 5-14z m312-210h-64l-77 313h57c6 0 10-1 14-4 4-3 6-6 7-11l32-173c2-7 4-14 6-23 1-8 3-17 4-26 3 9 6 18 9 26 4 9 7 16 11 23l73 173c1 2 2 4 4 6 2 2 4 3 6 5 2 1 4 2 7 3 3 1 5 1 8 1h57l-154-313z m423 0h-37c-5 0-10 1-13 2-4 2-7 5-10 9l-109 194c-1-4-1-8-1-12-1-4-1-7-1-10l-22-183h-62l39 313h37c3 0 6 0 8 0 2 0 4-1 5-1 2-1 3-2 4-4s3-3 5-5l110-194c0 5 0 10 1 14 0 5 1 9 1 13l21 177h62l-38-313z" horiz-adv-x="1000" />
52 86
53 <glyph glyph-name="hg-inv" unicode="&#xe81b;" d="M927 841h-853c-36 0-65-29-65-65v-853c0-36 29-65 65-65h853c36 0 65 29 65 65v853c0 36-29 65-65 65z m-483-648h-70l16 133h-113l-17-133h-70l39 313h70l-16-132h113l16 132h71l-39-313z m177 101c3-11 8-20 14-27 7-8 14-14 23-18 8-4 18-6 28-6 9 0 16 1 23 3 7 1 14 3 20 6l6 51h-27c-4 0-7 1-9 3-3 3-3 6-3 9l5 39h104l-16-131c-8-6-16-11-25-15-9-5-18-8-27-11-9-2-19-4-30-6-10-1-21-2-33-2-19 0-37 4-53 11-16 7-30 17-41 29-11 13-20 28-26 45-7 17-10 35-10 55 0 17 2 34 6 50 4 15 10 30 17 43 7 14 16 26 26 36 10 11 22 20 34 28 13 7 27 13 41 17 14 4 30 7 46 7 13 0 25-2 36-4 11-3 20-6 29-10 8-4 16-9 23-14 7-5 13-11 18-17l-23-28c-4-5-8-8-13-9-5-1-11 0-16 3-5 4-10 7-14 9-5 3-9 5-14 6-4 2-9 3-14 4-5 1-11 1-17 1-14 0-27-3-38-8-11-6-21-14-29-25-8-10-15-23-19-38-5-15-7-31-7-49 0-13 2-26 5-37z" horiz-adv-x="1000" />
87 <glyph glyph-name="comment-add" unicode="&#xe82f;" d="M952 258v317c0 7 0 13 0 20-1 12-4 24-8 36-7 22-20 43-37 59-16 17-36 30-58 37-12 4-25 7-37 8-7 1-13 1-19 1h-576c-13 0-26 0-38-2-13-2-25-5-36-10-22-9-41-23-57-40-15-18-27-39-33-62-3-12-5-25-5-38-1-13 0-26 0-39v-557c0-9 5-17 13-21 6-3 15-3 21 0 3 1 5 3 7 5 2 2 4 5 7 7 4 5 9 9 14 14l28 28c9 10 19 19 28 29 9 9 19 18 28 27 4 5 8 9 14 10 2 1 5 1 8 1h567c13 0 25 0 38 2 24 4 47 13 66 27 19 13 35 31 46 51 12 22 19 46 19 71 1 6 0 13 0 19z m-69 307v-317c0-7 0-13 0-19-1-6-3-13-5-18-4-10-9-20-16-28-15-17-37-27-59-28-7 0-13 0-19 0h-576c-7 0-13 0-20 0-3 0-6 0-9-1-3-1-5-2-7-4-2-2-4-4-6-6-3-2-5-4-7-7-5-4-10-9-14-14-10-9-19-18-28-28v485c0 12 2 24 7 35 4 10 10 19 18 27 16 16 38 25 60 25h590c6 0 12 0 18-1 22-3 42-15 56-33 7-9 12-20 15-31 1-5 2-12 2-18 1-6 0-13 0-19z m-214-117h-131c-4 0-11 8-11 12v126c0 8-8 16-12 16h-50c-7 0-15-8-15-12v-130c0-4-8-12-12-12h-126c-8 0-16-8-16-11v-50c0-8 8-16 12-16h127c7 0 15-7 15-11v-127c0-8 8-15 11-15h50c8 0 16 7 16 11v127c0 8 7 15 11 15h127c8 0 15 8 15 12v50c0 7-7 15-11 15z" horiz-adv-x="1000" />
88
89 <glyph glyph-name="comment-toggle" unicode="&#xe830;" d="M798 736h-596c-85 0-154-69-154-155v-593c0-19 22-29 36-20 2 1 5 3 7 5l109 109c2 2 5 4 8 5 2 1 4 1 6 1h584c85 0 154 69 154 155v338c0 86-69 155-154 155z m-680-639v484c0 47 38 85 86 85h476c-86-84-504-511-509-515l-53-54z" horiz-adv-x="1000" />
54 90
55 <glyph glyph-name="minus" unicode="&#xe81c;" d="M895 269h-790c-5 0-10 5-10 10v142c0 5 5 10 10 10h793c5 0 9-5 9-10v-142c-2-5-7-10-12-10z" horiz-adv-x="1000" />
91 <glyph glyph-name="rhodecode" unicode="&#xe831;" d="M175 633c-2-4-3-8-4-12-3-10-6-20-9-30-3-13-7-25-11-38-3-11-6-23-10-35-2-7-4-15-6-22-1-1-1-2-1-4 0 0 0 0 0 0 0-1 1-2 1-2 2-7 5-14 7-21 4-11 8-22 12-33 4-12 9-25 13-37 4-11 8-23 12-34 3-7 5-14 7-21 1-1 1-2 2-3 0-1 1-1 1-2 4-6 8-12 11-17 7-10 13-19 19-29 7-11 14-22 22-33 6-10 13-21 20-31 5-7 9-15 14-22 1-2 3-4 4-5 0-1 1-1 1-2 3-3 6-5 8-8 7-6 13-12 19-19 9-8 17-16 25-24 10-10 19-19 29-28 9-9 18-18 27-27 8-8 16-15 23-23 5-5 11-10 16-15 1-1 3-3 5-5 7-5 14-10 21-15 11-8 21-15 31-23 4-2 7-5 11-7 0-1 1-2 2-2 0 0 0-1 1 0 7 3 14 7 21 11 11 6 23 11 34 17 6 4 12 7 19 10 0 0 0 1 1 1 1 2 2 3 3 5 4 5 8 10 13 15 6 8 12 16 18 24 8 9 15 19 23 28 8 11 16 21 24 31 8 11 16 21 24 31 8 10 15 19 23 28 6 8 12 16 18 24 4 5 8 10 12 15 2 2 3 3 4 5 0 0 0 0 0 0-1 1-2 1-3 1-3 0-6 1-9 2-5 1-10 2-15 3-6 2-13 4-20 5-8 3-16 5-24 7-9 3-19 6-28 9-10 3-21 7-31 11-12 4-23 8-34 13-12 5-24 10-36 15-13 6-26 12-38 18-13 7-26 14-39 21-13 7-27 15-39 23-14 9-27 17-40 27-13 9-26 19-39 29-13 11-25 22-37 33-13 11-25 23-36 36-12 13-23 26-34 40-11 14-21 28-31 43-9 15-19 31-27 47 0 1 0 1 0 1z m-3 3c-1-5-3-9-4-14-3-10-7-21-10-32-4-12-8-25-12-37-3-10-6-20-9-30-1-3-2-6-3-8 0-1 0-2 0-2 1-5 3-10 5-15 3-10 6-20 10-30 4-12 8-24 12-37 4-12 8-24 12-36 3-9 6-18 9-26 1-3 1-5 2-8 0 0 1-1 1-2 2-4 5-8 7-12 5-10 10-19 15-28 6-11 12-23 19-34 6-11 12-22 18-33 4-8 8-15 12-23 1-2 2-4 4-6 4-5 8-9 13-14 7-8 15-16 23-24 9-10 18-20 26-29 9-9 17-18 25-26 5-6 10-11 15-17 2-1 3-3 5-5 5-5 11-11 17-17 9-8 17-17 26-26 9-9 18-18 27-27 7-7 14-14 21-21 2-2 3-3 5-5 0 0 1-1 1-1 0 0 1 0 1 0 11 2 22 3 32 5 9 1 17 2 26 3 0 0 1 1 1 1 1 1 2 3 4 4 4 5 9 10 13 15 7 8 14 15 20 22 9 9 17 18 25 27 9 10 18 20 27 30 8 9 17 19 26 29 8 9 16 17 24 26 7 7 13 15 20 22 4 5 8 9 13 14 1 1 2 2 3 3 0 1 1 1 1 1 0 1-3 1-3 1-3 1-7 2-10 3-4 2-9 3-14 5-6 2-13 4-19 6-8 3-16 6-24 9-9 3-18 7-27 11-10 4-20 8-30 13-11 5-22 10-33 16-12 5-23 11-35 18-12 6-24 13-36 20-12 8-25 16-37 24-13 8-25 17-37 26-13 10-25 19-38 29-12 11-24 21-36 33-12 11-24 23-35 35-11 13-22 25-33 39-10 13-21 27-30 42-10 15-19 30-27 45-9 16-17 32-24 48z m-2 10c-1-4-2-8-3-11-1-10-3-19-5-29-2-12-5-25-7-37-3-13-5-26-8-39-1-10-3-20-5-30-1-5-2-10-3-15 0-1 0-1 0-2 1-3 2-5 3-8 3-9 7-19 10-29 4-12 9-25 13-37 4-11 8-22 11-33 2-5 4-11 6-16 0-1 1-2 1-2 1-3 2-5 4-7 4-9 8-18 13-27 6-12 11-23 17-35 6-11 11-22 17-33 3-7 7-14 11-21 0-2 1-3 1-4 1-1 2-1 2-2 5-6 9-11 14-17 8-9 15-18 22-27 9-10 17-20 26-30 7-9 15-18 22-27 5-6 10-11 15-17 0-1 1-2 2-3 0 0 0 0 0 0 1-1 2-1 3-2 7-4 14-9 21-14 10-7 21-14 31-22 11-7 21-14 31-20 6-4 12-9 18-13 3-2 7-5 10-8 10-8 19-16 29-24 7-5 13-11 20-17 1 0 1 0 1 1 1 1 2 2 3 3 4 4 8 8 12 13 6 6 12 13 18 20 8 8 16 17 23 25 9 10 18 19 26 29 9 9 18 19 27 29 9 9 18 19 26 28 8 9 16 17 23 26 6 6 13 13 19 20 4 4 7 8 11 12 1 2 3 3 4 4 0 0 0 0 0 0 0 0 0 0 0 0 0 0-3 1-3 1-3 1-6 2-9 2-5 2-10 4-15 5-6 2-12 5-18 7-8 3-16 6-24 9-8 4-17 8-26 12-10 4-20 9-30 13-11 6-22 11-32 16-12 6-23 13-35 19-12 7-23 14-35 21-13 8-25 16-37 24-12 8-25 17-37 26-12 9-24 19-36 29-13 10-25 21-36 32-12 11-24 22-35 34-12 12-22 25-33 38-11 13-21 26-30 40-10 14-19 29-28 44-9 15-17 30-24 46-4 10-8 20-12 30z m696 21c-2 4-5 7-9 9-5 3-11 5-16 8-11 4-23 9-34 13-23 8-47 14-71 20-24 6-49 12-74 17-25 6-50 10-76 15-25 4-50 8-75 10-13 1-26 1-39 0-6-1-13-2-19-3-6-1-13-2-19-3-26-4-51-9-77-14-25-5-50-10-75-16-25-5-49-12-74-20-12-4-24-9-36-13-6-3-11-5-17-8-3-1-6-2-9-3-3-1-5-2-8-4-4-2-7-5-10-9-1-2-2-4-3-7-1-3-2-6-3-9-4-11-7-24-9-36-5-24-7-49-6-74 0-13 1-25 3-38 1-12 3-25 5-37 5-25 12-50 20-74 4-12 8-24 13-36 4-11 10-22 15-33 10-21 21-42 34-62 12-20 25-39 39-58 14-19 28-37 43-55 16-18 33-36 50-54 17-18 34-35 52-52 18-17 36-33 55-49 10-7 19-15 28-22 10-8 19-15 28-23 2-2 5-4 7-7 0 0 1-1 1-1 0 0 1 0 1 0 0 0 1 0 2 0 4 4 9 8 14 11 9 8 19 15 28 23 18 15 36 31 54 47 18 16 35 32 52 49 17 16 33 34 49 51 16 18 32 37 47 56 14 18 28 38 41 57 13 20 25 40 36 61 11 21 21 43 30 65 9 22 17 45 23 68 6 23 11 47 13 70 3 24 3 49 2 73 0 3-1 6-2 9 0 3-1 6-2 9-1 6-2 12-3 18-3 11-5 22-8 33-4 9-7 19-11 28-2 5 13-29 0 0z m-51-210c-7-25-15-49-26-73-9-22-19-44-30-64-12-21-24-40-37-59-13-19-27-38-42-56-15-18-31-36-47-54-17-18-34-36-52-53-18-17-37-34-56-50-9-7-19-15-28-23-1 0-2-1-2-1-1 0-2 0-2 0-1 0-2 1-2 1 0 0-1 1-1 1-2 1-3 3-4 4-4 3-9 7-14 11-2 1-4 3-7 5-2 2-4 4-6 6-5 4-9 8-14 13-9 8-18 17-27 25-10 9-18 18-27 27-4 4-8 9-13 13-4 4-8 9-12 13-17 17-33 35-49 53-15 18-30 37-44 57-14 20-27 40-38 61-12 21-23 42-32 64-10 22-18 45-25 67-2 6-4 12-5 19-1 6-2 12-3 19-2 13-4 26-4 39-1 13-2 26-1 39 0 12 1 25 3 37 0 4 0 7 1 10 0 1 0 3 0 5 1 1 1 3 1 4 0 3 1 5 2 7 0 2 0 3 0 4 0 1 1 2 2 3 1 0 2 1 3 2 0 0 1 0 1 1 1 0 2 0 3 1 3 1 6 2 9 3 6 2 12 5 18 7 23 8 47 16 72 23 12 3 24 6 37 9 6 1 12 2 18 4 7 1 13 2 19 4 26 5 51 9 77 13 13 1 26 3 39 5 3 0 7 1 10 1 1 1 3 1 4 1 2 0 3 0 4 0 6 0 12 0 17-1 1 0 2-1 4-1 1 0 3-1 4-1 3 0 6-1 9-1 7-1 13-2 19-3 13-2 25-4 38-6 25-4 51-8 76-13 25-6 50-12 75-19 12-4 24-8 37-12 6-2 12-4 18-6 3-1 6-2 9-3 1-1 3-1 4-2 1 0 1 0 2 0 1-1 2-1 2-1 2-2 3-2 4-4 1-1 1-1 1-2 0-1 0-2 0-2 1-1 1-2 1-3 2-6 3-13 4-19 1-7 2-13 3-20 0-3 0-6 0-9 0-1 0-2 0-2 0-1 0-2 0-3 1-1 1-3 1-5 5-23 7-48 5-72-1-13-3-26-6-38-8-29 8 35 0 0z m-197 0c-2 4-3 9-5 13 0 1 0 1 0 2-1 0 0 1-1 1 0 1 0 2 0 2 0 1-1 2-1 3-1 2-3 4-4 5-2 2-5 4-7 4 2 2 4 3 7 5 1 1 2 2 3 2 1 1 2 1 2 2 0 1 0 1 0 2 1 0 1 1 2 1 0 1 1 2 1 4 0 2 0 4 0 6 0 3 0 5 0 7 0 3 0 5-1 7-1 6-4 10-8 14-1 2-3 3-5 4-3 2-5 4-8 5-3 1-6 2-9 3-3 0-5 0-7 0-3 0-6 0-8 0-13 0-25 0-37 0-5 0-10 0-14 0-1 0-2 0-3 0 0 0 0-4 0-5 0-3 0-6 0-9 0-1 0-2 0-3 0-1 0-1 1-1 1 0 12 0 12 0 0-8 0-16 0-24 0-13 0-25 0-38 0-4 0-7 0-11 0 0 0-1 0-1-3 0-5 0-8 0-1 0-2 0-4 0 0 0-1 0-1-1 0-2 0-4 0-6 0-1 0-14 0-14 10 0 19 0 29 0 5 0 11 0 16 0 1 0 3 0 4 0 0 0 0 3 0 3 0 6 0 11 0 17 0 1 0 1-1 1-1 0-2 0-4 0-1 0-3 0-4 0 0 0-1-1-1 0 0 5 0 10 0 15 0 2 0 5 0 8 0 1 0 1 0 2 0 0 0 0 1 0 2 0 5 0 8 0 2 0 4 0 6 0 1 0 3 0 4 0 1 0 2-1 3-2 1-1 2-2 3-3 0-1 0-1 0-2 0-2 1-3 1-4 1-1 1-2 2-3 0-1 0-1 0-1 0-1 0-2 0-2 1-6 2-12 3-17 1-3 1-5 2-8 0 0 0-1 0-1 0 0 0 0 0 0 11 0 21 0 32 0 0 0 1 0 1 0 0 0 0 0 0 0 0 3 0 5 0 8 0 5 0 10 0 15 0 0 0 0 0 0-1-2-1-4-2-5z m-26 53c0-2-3-3-4-4-1 0-1-1-1-1 0 0-1 0-1 0 0 0-1 0-1 0-1-1-1-2-2-2-1 0-2 0-3 0-2 0-4 0-5 0-1 0-2 0-2 0-3 0-7 0-10 0 0 0-4 0-4 0 0 9 0 19 0 28 0 0 13 0 14 0 4 0 8 0 12-1 1 0 3-1 4-2 1 0 2-1 3-2 1-2 2-4 3-6 0-1 0-1 0-2-1-1-1-1-1-2-1-1-1-1-1-2-1-1-1-2-1-4z m131-53c0 9 0 18 0 27 0 9-2 18-8 24-7 7-19 8-28 7-2 0-4 0-6-1-1 0-1-1-2-2-1 0-2 0-2-1-3-1-6-3-8-6 0 9 0 18 0 27 0 6 0 12 0 18 0 2 0 3 0 5 0 1 0 1 0 1-11 0-22 0-32 0-1 0-3 0-4 0 0 0 0-4 0-4 0-5 0-11 0-16 0 0 1 0 1 0 1 0 3 0 4 0 3 0 5 0 8 0 0 0 0-5 0-6 0-11 0-23 0-34 0-11 0-22 0-33 0-1 0-2 0-3 0-1 0-1-1-1-3 0-6 0-9 0-1 0-2 0-3 0 0 0 0-1 0-1 0-6 0-11 0-17 0-1 0-1 0-2 0 0 0 0 0 0 2 0 3 0 4 0 12 0 24 0 36 0 0 0 9 0 9 0 0 5 0 10 0 15 0 1 0 3 0 5 0 0-6 0-7 0 0 0-6 0-6 0 0 1 0 3 0 4 0 6 0 12 0 18 0 3 0 5 0 7 0 1 0 1 0 2 0 0 1 1 2 2 1 1 2 2 3 2 1 1 1 1 2 1 1 0 1 0 1 1 2 1 3 1 4 1 3 1 5 0 7-1 1-1 2-2 3-3 1-1 2-2 2-3 1-2 1-4 1-6 0-3 0-7 0-11 0-11 0-22 0-33 0-1 0-2 1-2 1 0 3 0 5 0 6 0 12 0 19 0 3 0 7 0 11 0 0 0 0 14 0 15 0 2 0 4 0 6-2-1-5-2-7-2z m7 122c-2 0-5 0-7 0-1 0-2 0-3 0 0 0 0 0 0 0-3-5-7-10-10-14-1-2-3-5-4-7 0 0-1-1-1-2 0 0 0-1 0-1 0-1 0-4 0-4 0 0 1 0 2 0 3 0 5 0 8 0 3 0 5 0 8 0 0 0 0-1 0-1 0-1 0-3 0-4 0-2 0-3 0-4 0-1 0-1 1-1 1 0 3 0 4 0 1 0 2 0 2 0 0 3 0 6 0 8 0 1 0 2 1 2 1 0 2 0 4 0 0 0 0 0 0 0 0 1 0 1 0 2 0 0 0 3 0 3-1 0-2 0-3 0-1 0-2 0-2 1 0 7 0 15 0 22z m-7-15c0-1 0-2 0-4 0-1 0-1 0-2 0 0 0-1 0-2 0 0-1 0-1 0-1 0-2 0-3 0-1 0-3 0-4 0 1 2 3 4 4 6 1 1 1 2 2 3 1 2 2 4 2 7 0-3 0-5 0-8z m41-2c-3 2-8 2-11 2-1 0-2 0-2 0 0 0 0 1 0 1 0 2 0 3 0 4 0 0 13 0 14 0 1 0 1 0 1 1 0 1 0 2 0 4 0 1 0 2 0 3 0 0-1 0-1 0-6 0-11 0-17 0-1 0-1 0-2 0 0 0 0-1 0-1-1-2-1-4-1-6-1-5-1-9-2-14 4 0 9 1 12-1 3-1 4-4 4-7-1-4-5-4-7-4-2 0-9-1-9 2-1-2-1-5-2-8 1 0 3-1 5-1 2-1 5-1 7-1 4 0 8 2 11 5 2 3 2 7 2 11 0 2 0 5 0 7 0 1-1 2-2 3 0 0 0 0 0 0-3 2 2 0 0 0z" horiz-adv-x="1000" />
92
93 <glyph glyph-name="up" unicode="&#xe832;" d="M687 254l-173 217c-8 9-22 9-29 0l-173-217c-9-12-1-29 15-29h345c16 0 24 17 15 29z" horiz-adv-x="1000" />
56 94
57 <glyph glyph-name="plus" unicode="&#xe81d;" d="M917 291v116c0 14-12 24-24 24h-283c-15 0-24 12-24 24v288c0 14-12 24-24 24h-117c-14 0-24-12-24-24v-283c0-15-11-24-23-24h-291c-14 0-24-12-24-24v-117c0-14 12-23 24-23h283c15 0 24-12 24-24v-284c0-14 12-23 24-23h117c14 0 24 11 24 23v279c0 14 11 24 23 24h284c19 0 31 12 31 24z" horiz-adv-x="1000" />
95 <glyph glyph-name="merge" unicode="&#xe833;" d="M200 110c0-72 58-131 130-131s130 59 130 131c0 45-24 86-60 109 18 139 133 179 202 190v-301c-38-23-65-64-65-112 0-72 59-130 130-130s130 58 130 130c0 48-26 89-65 112v487c39 23 65 64 65 112 0 72-58 130-130 130s-130-58-130-130c0-48 27-89 65-112v-55c-60-8-162-32-238-108-54-54-86-124-94-208-42-22-70-65-70-114z m468-158c-24 0-44 20-44 43s20 44 44 44c24 0 43-20 43-44s-19-43-43-43z m0 798c24 0 43-19 43-43s-20-43-43-43c-24 0-44 19-44 43s20 43 44 43z m-338-684c-24 0-43 20-43 43s19 44 43 44c24 0 43-20 43-44s-19-43-43-43z" horiz-adv-x="1000" />
58 96
59 <glyph glyph-name="remove" unicode="&#xe81e;" d="M836 602l-84 84c-9 9-26 9-35 0l-200-200c-10-10-26-10-36 0l-200 200c-9 9-26 9-36 0l-83-84c-9-9-9-26 0-35l200-200c10-10 10-26 0-36l-200-200c-9-9-9-26 0-36l83-83c10-9 27-9 36 0l200 200c10 10 26 10 36 0l200-200c9-9 26-9 35 0l84 83c9 10 9 27 0 36l-200 200c-10 10-10 26 0 36l200 200c9 12 9 26 0 35z" horiz-adv-x="1000" />
97 <glyph glyph-name="spin-alt" unicode="&#xe834;" d="M498 850c-114 0-228-39-320-116l0 0c173 140 428 130 588-31 134-134 164-332 89-495-10-29-5-50 12-68 21-20 61-23 84 0 3 3 12 15 15 24 71 180 33 393-112 539-99 98-228 147-356 147z m-409-274c-14 0-29-5-39-16-3-3-13-15-15-24-71-180-34-393 112-539 185-185 479-195 676-31l0 0c-173-140-428-130-589 31-134 134-163 333-89 495 11 29 6 50-12 68-11 11-27 17-44 16z" horiz-adv-x="1001" />
98
99 <glyph glyph-name="spin" unicode="&#xe838;" d="M462 850c-6 0-11-5-11-11l0-183 0 0c0-6 5-11 11-11l69 0c1 0 1 0 1 0 7 0 12 5 12 11l0 183 0 0c0 6-5 11-12 11l-69 0c0 0 0 0-1 0z m250-47c-4 1-8-2-10-5l-91-158 0 0c-4-6-2-13 4-16l60-34c0-1 0-1 0-1 6-3 13-1 16 4l91 158c3 6 2 13-4 16l-61 35c-1 1-3 1-5 1z m-428-2c-2 0-4-1-6-2l-61-35c-5-3-7-10-4-16l91-157c0 0 0 0 0 0 3-6 10-8 16-5l61 35c5 4 7 11 4 16l-91 157c0 1 0 1 0 1-2 4-6 6-10 6z m620-163c-2 0-4 0-6-1l-157-91c0 0 0 0 0 0-6-3-8-10-5-16l35-61c4-5 11-7 16-4l157 91c1 0 1 0 1 0 6 3 7 11 4 16l-35 61c-2 4-6 6-10 5z m-810-4c-5 0-9-2-11-6l-35-61c-3-5-1-12 4-15l158-91 0 0c6-4 13-2 16 4l35 60c0 0 0 0 0 0 3 6 1 13-4 16l-158 91c-2 1-4 2-5 2z m712-235l0 0c-6 0-11-5-11-11l0-69c0-1 0-1 0-1 0-7 5-12 11-12l183 0 0 0c6 0 11 5 11 12l0 69c0 0 0 0 0 1 0 6-5 11-11 11l-183 0z m-794-5l0 0c-7 0-12-5-12-12l0-69c0 0 0 0 0-1 0-6 5-11 12-11l182 0 0 0c6 0 11 5 11 11l0 69c0 1 0 1 0 1 0 7-5 12-11 12l-182 0z m772-153c-4 0-8-2-10-6l-34-60c-1 0-1 0-1 0-3-6-1-13 4-16l158-91c6-3 13-1 16 4l35 61c3 5 1 12-4 15l-158 92 0 0c-2 1-4 1-6 1z m-566-5c-1 0-3 0-5-1l-157-91c0 0-1 0-1 0-5-3-7-10-4-16l35-61c3-5 10-7 16-4l157 91c0 0 0 0 0 0 6 3 8 10 5 16l-35 61c-3 3-7 6-11 5z m468-121c-2 0-4 0-6-1l-61-35c-5-4-7-11-4-16l91-157c0-1 0-1 0-1 3-6 11-7 16-4l61 35c5 3 7 10 4 16l-91 157c0 0 0 0 0 0-2 4-6 6-10 6z m-367-2c-4 0-8-2-10-6l-91-158c-3-6-1-13 4-16l61-35c5-3 12-1 15 4l92 158 0 0c3 6 1 13-5 16l-60 35c0 0 0 0 0 0-2 1-4 1-6 2z m149-58c-7 0-12-5-12-11l0-183 0 0c0-6 5-11 12-11l69 0c0 0 0 0 1 0 6 0 11 5 11 11l0 183 0 0c0 6-5 11-11 11l-69 0c-1 0-1 0-1 0z" horiz-adv-x="1000" />
60 100
61 <glyph glyph-name="rhodecode" unicode="&#xe81f;" d="M175 633c-2-4-3-8-4-12-3-10-6-20-9-30-3-13-7-25-11-38-3-11-6-23-10-35-2-7-4-15-6-22-1-1-1-2-1-4 0 0 0 0 0 0 0-1 1-2 1-2 2-7 5-14 7-21 4-11 8-22 12-33 4-12 9-25 13-37 4-11 8-23 12-34 3-7 5-14 7-21 1-1 1-2 2-3 0-1 1-1 1-2 4-6 8-12 11-17 7-10 13-19 19-29 7-11 14-22 22-33 6-10 13-21 20-31 5-7 9-15 14-22 1-2 3-4 4-5 0-1 1-1 1-2 3-3 6-5 8-8 7-6 13-12 19-19 9-8 17-16 25-24 10-10 19-19 29-28 9-9 18-18 27-27 8-8 16-15 23-23 5-5 11-10 16-15 1-1 3-3 5-5 7-5 14-10 21-15 11-8 21-15 31-23 4-2 7-5 11-7 0-1 1-2 2-2 0 0 0-1 1 0 7 3 14 7 21 11 11 6 23 11 34 17 6 4 12 7 19 10 0 0 0 1 1 1 1 2 2 3 3 5 4 5 8 10 13 15 6 8 12 16 18 24 8 9 15 19 23 28 8 11 16 21 24 31 8 11 16 21 24 31 8 10 15 19 23 28 6 8 12 16 18 24 4 5 8 10 12 15 2 2 3 3 4 5 0 0 0 0 0 0-1 1-2 1-3 1-3 0-6 1-9 2-5 1-10 2-15 3-6 2-13 4-20 5-8 3-16 5-24 7-9 3-19 6-28 9-10 3-21 7-31 11-12 4-23 8-34 13-12 5-24 10-36 15-13 6-26 12-38 18-13 7-26 14-39 21-13 7-27 15-39 23-14 9-27 17-40 27-13 9-26 19-39 29-13 11-25 22-37 33-13 11-25 23-36 36-12 13-23 26-34 40-11 14-21 28-31 43-9 15-19 31-27 47 0 1 0 1 0 1z m-3 3c-1-5-3-9-4-14-3-10-7-21-10-32-4-12-8-25-12-37-3-10-6-20-9-30-1-3-2-6-3-8 0-1 0-2 0-2 1-5 3-10 5-15 3-10 6-20 10-30 4-12 8-24 12-37 4-12 8-24 12-36 3-9 6-18 9-26 1-3 1-5 2-8 0 0 1-1 1-2 2-4 5-8 7-12 5-10 10-19 15-28 6-11 12-23 19-34 6-11 12-22 18-33 4-8 8-15 12-23 1-2 2-4 4-6 4-5 8-9 13-14 7-8 15-16 23-24 9-10 18-20 26-29 9-9 17-18 25-26 5-6 10-11 15-17 2-1 3-3 5-5 5-5 11-11 17-17 9-8 17-17 26-26 9-9 18-18 27-27 7-7 14-14 21-21 2-2 3-3 5-5 0 0 1-1 1-1 0 0 1 0 1 0 11 2 22 3 32 5 9 1 17 2 26 3 0 0 1 1 1 1 1 1 2 3 4 4 4 5 9 10 13 15 7 8 14 15 20 22 9 9 17 18 25 27 9 10 18 20 27 30 8 9 17 19 26 29 8 9 16 17 24 26 7 7 13 15 20 22 4 5 8 9 13 14 1 1 2 2 3 3 0 1 1 1 1 1 0 1-3 1-3 1-3 1-7 2-10 3-4 2-9 3-14 5-6 2-13 4-19 6-8 3-16 6-24 9-9 3-18 7-27 11-10 4-20 8-30 13-11 5-22 10-33 16-12 5-23 11-35 18-12 6-24 13-36 20-12 8-25 16-37 24-13 8-25 17-37 26-13 10-25 19-38 29-12 11-24 21-36 33-12 11-24 23-35 35-11 13-22 25-33 39-10 13-21 27-30 42-10 15-19 30-27 45-9 16-17 32-24 48z m-2 10c-1-4-2-8-3-11-1-10-3-19-5-29-2-12-5-25-7-37-3-13-5-26-8-39-1-10-3-20-5-30-1-5-2-10-3-15 0-1 0-1 0-2 1-3 2-5 3-8 3-9 7-19 10-29 4-12 9-25 13-37 4-11 8-22 11-33 2-5 4-11 6-16 0-1 1-2 1-2 1-3 2-5 4-7 4-9 8-18 13-27 6-12 11-23 17-35 6-11 11-22 17-33 3-7 7-14 11-21 0-2 1-3 1-4 1-1 2-1 2-2 5-6 9-11 14-17 8-9 15-18 22-27 9-10 17-20 26-30 7-9 15-18 22-27 5-6 10-11 15-17 0-1 1-2 2-3 0 0 0 0 0 0 1-1 2-1 3-2 7-4 14-9 21-14 10-7 21-14 31-22 11-7 21-14 31-20 6-4 12-9 18-13 3-2 7-5 10-8 10-8 19-16 29-24 7-5 13-11 20-17 1 0 1 0 1 1 1 1 2 2 3 3 4 4 8 8 12 13 6 6 12 13 18 20 8 8 16 17 23 25 9 10 18 19 26 29 9 9 18 19 27 29 9 9 18 19 26 28 8 9 16 17 23 26 6 6 13 13 19 20 4 4 7 8 11 12 1 2 3 3 4 4 0 0 0 0 0 0 0 0 0 0 0 0 0 0-3 1-3 1-3 1-6 2-9 2-5 2-10 4-15 5-6 2-12 5-18 7-8 3-16 6-24 9-8 4-17 8-26 12-10 4-20 9-30 13-11 6-22 11-32 16-12 6-23 13-35 19-12 7-23 14-35 21-13 8-25 16-37 24-12 8-25 17-37 26-12 9-24 19-36 29-13 10-25 21-36 32-12 11-24 22-35 34-12 12-22 25-33 38-11 13-21 26-30 40-10 14-19 29-28 44-9 15-17 30-24 46-4 10-8 20-12 30z m696 21c-2 4-5 7-9 9-5 3-11 5-16 8-11 4-23 9-34 13-23 8-47 14-71 20-24 6-49 12-74 17-25 6-50 10-76 15-25 4-50 8-75 10-13 1-26 1-39 0-6-1-13-2-19-3-6-1-13-2-19-3-26-4-51-9-77-14-25-5-50-10-75-16-25-5-49-12-74-20-12-4-24-9-36-13-6-3-11-5-17-8-3-1-6-2-9-3-3-1-5-2-8-4-4-2-7-5-10-9-1-2-2-4-3-7-1-3-2-6-3-9-4-11-7-24-9-36-5-24-7-49-6-74 0-13 1-25 3-38 1-12 3-25 5-37 5-25 12-50 20-74 4-12 8-24 13-36 4-11 10-22 15-33 10-21 21-42 34-62 12-20 25-39 39-58 14-19 28-37 43-55 16-18 33-36 50-54 17-18 34-35 52-52 18-17 36-33 55-49 10-7 19-15 28-22 10-8 19-15 28-23 2-2 5-4 7-7 0 0 1-1 1-1 0 0 1 0 1 0 0 0 1 0 2 0 4 4 9 8 14 11 9 8 19 15 28 23 18 15 36 31 54 47 18 16 35 32 52 49 17 16 33 34 49 51 16 18 32 37 47 56 14 18 28 38 41 57 13 20 25 40 36 61 11 21 21 43 30 65 9 22 17 45 23 68 6 23 11 47 13 70 3 24 3 49 2 73 0 3-1 6-2 9 0 3-1 6-2 9-1 6-2 12-3 18-3 11-5 22-8 33-4 9-7 19-11 28-2 5 13-29 0 0z m-51-210c-7-25-15-49-26-73-9-22-19-44-30-64-12-21-24-40-37-59-13-19-27-38-42-56-15-18-31-36-47-54-17-18-34-36-52-53-18-17-37-34-56-50-9-7-19-15-28-23-1 0-2-1-2-1-1 0-2 0-2 0-1 0-2 1-2 1 0 0-1 1-1 1-2 1-3 3-4 4-4 3-9 7-14 11-2 1-4 3-7 5-2 2-4 4-6 6-5 4-9 8-14 13-9 8-18 17-27 25-10 9-18 18-27 27-4 4-8 9-13 13-4 4-8 9-12 13-17 17-33 35-49 53-15 18-30 37-44 57-14 20-27 40-38 61-12 21-23 42-32 64-10 22-18 45-25 67-2 6-4 12-5 19-1 6-2 12-3 19-2 13-4 26-4 39-1 13-2 26-1 39 0 12 1 25 3 37 0 4 0 7 1 10 0 1 0 3 0 5 1 1 1 3 1 4 0 3 1 5 2 7 0 2 0 3 0 4 0 1 1 2 2 3 1 0 2 1 3 2 0 0 1 0 1 1 1 0 2 0 3 1 3 1 6 2 9 3 6 2 12 5 18 7 23 8 47 16 72 23 12 3 24 6 37 9 6 1 12 2 18 4 7 1 13 2 19 4 26 5 51 9 77 13 13 1 26 3 39 5 3 0 7 1 10 1 1 1 3 1 4 1 2 0 3 0 4 0 6 0 12 0 17-1 1 0 2-1 4-1 1 0 3-1 4-1 3 0 6-1 9-1 7-1 13-2 19-3 13-2 25-4 38-6 25-4 51-8 76-13 25-6 50-12 75-19 12-4 24-8 37-12 6-2 12-4 18-6 3-1 6-2 9-3 1-1 3-1 4-2 1 0 1 0 2 0 1-1 2-1 2-1 2-2 3-2 4-4 1-1 1-1 1-2 0-1 0-2 0-2 1-1 1-2 1-3 2-6 3-13 4-19 1-7 2-13 3-20 0-3 0-6 0-9 0-1 0-2 0-2 0-1 0-2 0-3 1-1 1-3 1-5 5-23 7-48 5-72-1-13-3-26-6-38-8-29 8 35 0 0z m-197 0c-2 4-3 9-5 13 0 1 0 1 0 2-1 0 0 1-1 1 0 1 0 2 0 2 0 1-1 2-1 3-1 2-3 4-4 5-2 2-5 4-7 4 2 2 4 3 7 5 1 1 2 2 3 2 1 1 2 1 2 2 0 1 0 1 0 2 1 0 1 1 2 1 0 1 1 2 1 4 0 2 0 4 0 6 0 3 0 5 0 7 0 3 0 5-1 7-1 6-4 10-8 14-1 2-3 3-5 4-3 2-5 4-8 5-3 1-6 2-9 3-3 0-5 0-7 0-3 0-6 0-8 0-13 0-25 0-37 0-5 0-10 0-14 0-1 0-2 0-3 0 0 0 0-4 0-5 0-3 0-6 0-9 0-1 0-2 0-3 0-1 0-1 1-1 1 0 12 0 12 0 0-8 0-16 0-24 0-13 0-25 0-38 0-4 0-7 0-11 0 0 0-1 0-1-3 0-5 0-8 0-1 0-2 0-4 0 0 0-1 0-1-1 0-2 0-4 0-6 0-1 0-14 0-14 10 0 19 0 29 0 5 0 11 0 16 0 1 0 3 0 4 0 0 0 0 3 0 3 0 6 0 11 0 17 0 1 0 1-1 1-1 0-2 0-4 0-1 0-3 0-4 0 0 0-1-1-1 0 0 5 0 10 0 15 0 2 0 5 0 8 0 1 0 1 0 2 0 0 0 0 1 0 2 0 5 0 8 0 2 0 4 0 6 0 1 0 3 0 4 0 1 0 2-1 3-2 1-1 2-2 3-3 0-1 0-1 0-2 0-2 1-3 1-4 1-1 1-2 2-3 0-1 0-1 0-1 0-1 0-2 0-2 1-6 2-12 3-17 1-3 1-5 2-8 0 0 0-1 0-1 0 0 0 0 0 0 11 0 21 0 32 0 0 0 1 0 1 0 0 0 0 0 0 0 0 3 0 5 0 8 0 5 0 10 0 15 0 0 0 0 0 0-1-2-1-4-2-5z m-26 53c0-2-3-3-4-4-1 0-1-1-1-1 0 0-1 0-1 0 0 0-1 0-1 0-1-1-1-2-2-2-1 0-2 0-3 0-2 0-4 0-5 0-1 0-2 0-2 0-3 0-7 0-10 0 0 0-4 0-4 0 0 9 0 19 0 28 0 0 13 0 14 0 4 0 8 0 12-1 1 0 3-1 4-2 1 0 2-1 3-2 1-2 2-4 3-6 0-1 0-1 0-2-1-1-1-1-1-2-1-1-1-1-1-2-1-1-1-2-1-4z m131-53c0 9 0 18 0 27 0 9-2 18-8 24-7 7-19 8-28 7-2 0-4 0-6-1-1 0-1-1-2-2-1 0-2 0-2-1-3-1-6-3-8-6 0 9 0 18 0 27 0 6 0 12 0 18 0 2 0 3 0 5 0 1 0 1 0 1-11 0-22 0-32 0-1 0-3 0-4 0 0 0 0-4 0-4 0-5 0-11 0-16 0 0 1 0 1 0 1 0 3 0 4 0 3 0 5 0 8 0 0 0 0-5 0-6 0-11 0-23 0-34 0-11 0-22 0-33 0-1 0-2 0-3 0-1 0-1-1-1-3 0-6 0-9 0-1 0-2 0-3 0 0 0 0-1 0-1 0-6 0-11 0-17 0-1 0-1 0-2 0 0 0 0 0 0 2 0 3 0 4 0 12 0 24 0 36 0 0 0 9 0 9 0 0 5 0 10 0 15 0 1 0 3 0 5 0 0-6 0-7 0 0 0-6 0-6 0 0 1 0 3 0 4 0 6 0 12 0 18 0 3 0 5 0 7 0 1 0 1 0 2 0 0 1 1 2 2 1 1 2 2 3 2 1 1 1 1 2 1 1 0 1 0 1 1 2 1 3 1 4 1 3 1 5 0 7-1 1-1 2-2 3-3 1-1 2-2 2-3 1-2 1-4 1-6 0-3 0-7 0-11 0-11 0-22 0-33 0-1 0-2 1-2 1 0 3 0 5 0 6 0 12 0 19 0 3 0 7 0 11 0 0 0 0 14 0 15 0 2 0 4 0 6-2-1-5-2-7-2z m7 122c-2 0-5 0-7 0-1 0-2 0-3 0 0 0 0 0 0 0-3-5-7-10-10-14-1-2-3-5-4-7 0 0-1-1-1-2 0 0 0-1 0-1 0-1 0-4 0-4 0 0 1 0 2 0 3 0 5 0 8 0 3 0 5 0 8 0 0 0 0-1 0-1 0-1 0-3 0-4 0-2 0-3 0-4 0-1 0-1 1-1 1 0 3 0 4 0 1 0 2 0 2 0 0 3 0 6 0 8 0 1 0 2 1 2 1 0 2 0 4 0 0 0 0 0 0 0 0 1 0 1 0 2 0 0 0 3 0 3-1 0-2 0-3 0-1 0-2 0-2 1 0 7 0 15 0 22z m-7-15c0-1 0-2 0-4 0-1 0-1 0-2 0 0 0-1 0-2 0 0-1 0-1 0-1 0-2 0-3 0-1 0-3 0-4 0 1 2 3 4 4 6 1 1 1 2 2 3 1 2 2 4 2 7 0-3 0-5 0-8z m41-2c-3 2-8 2-11 2-1 0-2 0-2 0 0 0 0 1 0 1 0 2 0 3 0 4 0 0 13 0 14 0 1 0 1 0 1 1 0 1 0 2 0 4 0 1 0 2 0 3 0 0-1 0-1 0-6 0-11 0-17 0-1 0-1 0-2 0 0 0 0-1 0-1-1-2-1-4-1-6-1-5-1-9-2-14 4 0 9 1 12-1 3-1 4-4 4-7-1-4-5-4-7-4-2 0-9-1-9 2-1-2-1-5-2-8 1 0 3-1 5-1 2-1 5-1 7-1 4 0 8 2 11 5 2 3 2 7 2 11 0 2 0 5 0 7 0 1-1 2-2 3 0 0 0 0 0 0-3 2 2 0 0 0z" horiz-adv-x="1000" />
101 <glyph glyph-name="docs" unicode="&#xf0c5;" d="M946 636q23 0 38-16t16-38v-678q0-23-16-38t-38-16h-535q-23 0-38 16t-16 38v160h-303q-23 0-38 16t-16 38v375q0 22 11 49t27 42l228 228q15 16 42 27t49 11h232q23 0 38-16t16-38v-183q38 23 71 23h232z m-303-119l-167-167h167v167z m-357 214l-167-167h167v167z m109-361l176 176v233h-214v-233q0-22-15-37t-38-16h-233v-357h286v143q0 22 11 49t27 42z m534-449v643h-215v-232q0-22-15-38t-38-15h-232v-358h500z" horiz-adv-x="1000" />
102
103 <glyph glyph-name="menu" unicode="&#xf0c9;" d="M857 100v-71q0-15-10-25t-26-11h-785q-15 0-25 11t-11 25v71q0 15 11 25t25 11h785q15 0 26-11t10-25z m0 286v-72q0-14-10-25t-26-10h-785q-15 0-25 10t-11 25v72q0 14 11 25t25 10h785q15 0 26-10t10-25z m0 285v-71q0-14-10-25t-26-11h-785q-15 0-25 11t-11 25v71q0 15 11 26t25 10h785q15 0 26-10t10-26z" horiz-adv-x="857.1" />
62 104
63 <glyph glyph-name="svn-inv" unicode="&#xe820;" d="M933 841h-852c-36 0-65-29-65-65v-853c0-36 29-65 65-65h852c36 0 66 29 66 65v853c0 36-30 65-66 65z m-765-438c3-4 7-7 13-10 5-3 11-6 18-8 7-3 14-5 21-8 7-3 14-6 21-10 7-4 13-9 18-14 5-6 10-13 13-20 3-8 5-18 5-29 0-16-3-30-8-44-6-14-14-26-24-37-10-10-22-18-37-24-15-7-31-10-49-10-9 0-18 1-27 3s-18 5-27 9c-8 4-16 8-23 13-7 5-13 10-18 17l25 32c2 3 4 5 7 6 3 2 6 3 9 3 4 0 8-2 12-4 3-3 8-6 12-10 5-3 10-6 16-9 6-3 14-4 23-4 13 0 23 3 30 10 7 7 10 18 10 32 0 6-1 12-4 16-4 4-8 7-13 10-5 3-11 6-18 8-7 2-14 5-21 7-7 3-14 6-21 9-6 4-12 8-18 14-5 6-9 13-12 21-3 8-5 18-5 30 0 14 3 28 8 40 5 13 12 25 22 35 10 9 22 17 36 23 14 6 29 9 47 9 9 0 17-1 26-3s16-4 23-8c7-3 14-7 20-11 6-5 11-10 15-15l-21-29c-2-3-5-6-7-7-3-2-6-3-9-3-3 0-7 1-10 3-3 3-7 5-11 8-4 2-9 4-14 7-5 2-12 3-19 3-6 0-12-1-17-3-5-2-9-4-12-8-4-3-6-7-8-11-1-5-2-10-2-15 0-5 2-10 5-14z m312-210h-64l-77 313h57c6 0 10-1 14-4 4-3 6-6 7-11l32-173c2-7 4-14 6-23 1-8 3-17 4-26 3 9 6 18 9 26 4 9 7 16 11 23l73 173c1 2 2 4 4 6 2 2 4 3 6 5 2 1 4 2 7 3 3 1 5 1 8 1h57l-154-313z m423 0h-37c-5 0-10 1-13 2-4 2-7 5-10 9l-109 194c-1-4-1-8-1-12-1-4-1-7-1-10l-22-183h-62l39 313h37c3 0 6 0 8 0 2 0 4-1 5-1 2-1 3-2 4-4s3-3 5-5l110-194c0 5 0 10 1 14 0 5 1 9 1 13l21 177h62l-38-313z" horiz-adv-x="1000" />
105 <glyph glyph-name="paste" unicode="&#xf0ea;" d="M429-79h500v358h-233q-22 0-37 15t-16 38v232h-214v-643z m142 804v36q0 7-5 12t-12 6h-393q-7 0-13-6t-5-12v-36q0-7 5-13t13-5h393q7 0 12 5t5 13z m143-375h167l-167 167v-167z m286-71v-375q0-23-16-38t-38-16h-535q-23 0-38 16t-16 38v89h-303q-23 0-38 16t-16 37v750q0 23 16 38t38 16h607q22 0 38-16t15-38v-183q12-7 20-15l228-228q16-15 27-42t11-49z" horiz-adv-x="1000" />
106
107 <glyph glyph-name="doc-text" unicode="&#xf0f6;" d="M819 638q16-16 27-42t11-50v-642q0-23-15-38t-38-16h-750q-23 0-38 16t-16 38v892q0 23 16 38t38 16h500q22 0 49-11t42-27z m-248 136v-210h210q-5 17-12 23l-175 175q-6 7-23 12z m215-853v572h-232q-23 0-38 16t-16 37v233h-429v-858h715z m-572 483q0 7 5 12t13 5h393q8 0 13-5t5-12v-36q0-8-5-13t-13-5h-393q-8 0-13 5t-5 13v36z m411-125q8 0 13-5t5-13v-36q0-8-5-13t-13-5h-393q-8 0-13 5t-5 13v36q0 8 5 13t13 5h393z m0-143q8 0 13-5t5-13v-36q0-8-5-13t-13-5h-393q-8 0-13 5t-5 13v36q0 8 5 13t13 5h393z" horiz-adv-x="857.1" />
64 108
65 <glyph glyph-name="tag" unicode="&#xe821;" d="M450 791l-371 11c-17 0-31-14-31-31l12-369c0-7 2-16 9-21l471-471c12-12 31-12 46 0l359 359c12 12 12 31 0 45l-474 467c-7 7-14 10-21 10z m-86-222c0-45-38-83-83-83s-83 38-83 83 38 83 83 83 83-38 83-83z" horiz-adv-x="1000" />
109 <glyph glyph-name="plus-squared" unicode="&#xf0fe;" d="M714 314v72q0 14-10 25t-25 10h-179v179q0 15-11 25t-25 11h-71q-15 0-25-11t-11-25v-179h-178q-15 0-25-10t-11-25v-72q0-14 11-25t25-10h178v-179q0-14 11-25t25-11h71q15 0 25 11t11 25v179h179q14 0 25 10t10 25z m143 304v-536q0-66-47-113t-114-48h-535q-67 0-114 48t-47 113v536q0 66 47 113t114 48h535q67 0 114-48t47-113z" horiz-adv-x="857.1" />
110
111 <glyph glyph-name="folder-empty" unicode="&#xf114;" d="M857 118v393q0 22-15 38t-38 15h-393q-23 0-38 16t-16 38v36q0 22-15 38t-38 15h-179q-22 0-38-15t-16-38v-536q0-22 16-38t38-16h679q22 0 38 16t15 38z m72 393v-393q0-51-37-88t-88-37h-679q-51 0-88 37t-37 88v536q0 51 37 88t88 37h179q51 0 88-37t37-88v-18h375q51 0 88-37t37-88z" horiz-adv-x="928.6" />
66 112
67 <glyph glyph-name="copy" unicode="&#xf0c5;" d="M946 636q23 0 38-16t16-38v-678q0-23-16-38t-38-16h-535q-23 0-38 16t-16 38v160h-303q-23 0-38 16t-16 38v375q0 22 11 49t27 42l228 228q15 16 42 27t49 11h232q23 0 38-16t16-38v-183q38 23 71 23h232z m-303-119l-167-167h167v167z m-357 214l-167-167h167v167z m109-361l176 176v233h-214v-233q0-22-15-37t-38-16h-233v-357h286v143q0 22 11 49t27 42z m534-449v643h-215v-232q0-22-15-38t-38-15h-232v-358h500z" horiz-adv-x="1000" />
113 <glyph glyph-name="folder-open-empty" unicode="&#xf115;" d="M994 331q0 19-30 19h-607q-22 0-48-12t-39-29l-164-203q-11-13-11-22 0-20 30-20h607q23 0 48 13t40 29l164 203q10 12 10 22z m-637 90h429v90q0 22-16 38t-38 15h-321q-23 0-38 16t-16 38v36q0 22-15 38t-38 15h-179q-22 0-38-15t-16-38v-476l143 175q25 30 65 49t78 19z m708-90q0-35-25-67l-165-203q-24-30-65-49t-78-19h-607q-51 0-88 37t-37 88v536q0 51 37 88t88 37h179q51 0 88-37t37-88v-18h303q52 0 88-37t37-88v-90h107q30 0 56-13t37-40q8-17 8-37z" horiz-adv-x="1071.4" />
114
115 <glyph glyph-name="minus-squared" unicode="&#xf146;" d="M714 314v72q0 14-10 25t-25 10h-500q-15 0-25-10t-11-25v-72q0-14 11-25t25-10h500q14 0 25 10t10 25z m143 304v-536q0-66-47-113t-114-48h-535q-67 0-114 48t-47 113v536q0 66 47 113t114 48h535q67 0 114-48t47-113z" horiz-adv-x="857.1" />
68 116
69 <glyph glyph-name="file-text" unicode="&#xf0f6;" d="M819 638q16-16 27-42t11-50v-642q0-23-15-38t-38-16h-750q-23 0-38 16t-16 38v892q0 23 16 38t38 16h500q22 0 49-11t42-27z m-248 136v-210h210q-5 17-12 23l-175 175q-6 7-23 12z m215-853v572h-232q-23 0-38 16t-16 37v233h-429v-858h715z m-572 483q0 7 5 12t13 5h393q8 0 13-5t5-12v-36q0-8-5-13t-13-5h-393q-8 0-13 5t-5 13v36z m411-125q8 0 13-5t5-13v-36q0-8-5-13t-13-5h-393q-8 0-13 5t-5 13v36q0 8 5 13t13 5h393z m0-143q8 0 13-5t5-13v-36q0-8-5-13t-13-5h-393q-8 0-13 5t-5 13v36q0 8 5 13t13 5h393z" horiz-adv-x="857.1" />
117 <glyph glyph-name="minus-squared-alt" unicode="&#xf147;" d="M643 404v-36q0-8-5-13t-13-5h-464q-8 0-13 5t-5 13v36q0 7 5 12t13 5h464q8 0 13-5t5-12z m71-250v464q0 37-26 63t-63 26h-464q-37 0-63-26t-27-63v-464q0-37 27-63t63-27h464q37 0 63 27t26 63z m72 464v-464q0-67-47-114t-114-47h-464q-67 0-114 47t-47 114v464q0 66 47 113t114 48h464q66 0 114-48t47-113z" horiz-adv-x="785.7" />
118
119 <glyph glyph-name="doc-inv" unicode="&#xf15b;" d="M571 564v264q13-8 21-16l227-228q8-7 16-20h-264z m-71-18q0-22 16-37t38-16h303v-589q0-23-15-38t-38-16h-750q-23 0-38 16t-16 38v892q0 23 16 38t38 16h446v-304z" horiz-adv-x="857.1" />
70 120
71 <glyph glyph-name="directory-empty" unicode="&#xf114;" d="M857 118v393q0 22-15 38t-38 15h-393q-23 0-38 16t-16 38v36q0 22-15 38t-38 15h-179q-22 0-38-15t-16-38v-536q0-22 16-38t38-16h679q22 0 38 16t15 38z m72 393v-393q0-51-37-88t-88-37h-679q-51 0-88 37t-37 88v536q0 51 37 88t88 37h179q51 0 88-37t37-88v-18h375q51 0 88-37t37-88z" horiz-adv-x="928.6" />
121 <glyph glyph-name="doc-text-inv" unicode="&#xf15c;" d="M819 584q8-7 16-20h-264v264q13-8 21-16z m-265-91h303v-589q0-23-15-38t-38-16h-750q-23 0-38 16t-16 38v892q0 23 16 38t38 16h446v-304q0-22 16-37t38-16z m89-411v36q0 8-5 13t-13 5h-393q-8 0-13-5t-5-13v-36q0-8 5-13t13-5h393q8 0 13 5t5 13z m0 143v36q0 8-5 13t-13 5h-393q-8 0-13-5t-5-13v-36q0-8 5-13t13-5h393q8 0 13 5t5 13z m0 143v36q0 7-5 12t-13 5h-393q-8 0-13-5t-5-12v-36q0-8 5-13t13-5h393q8 0 13 5t5 13z" horiz-adv-x="857.1" />
72 122
73 <glyph glyph-name="file-text-inv" unicode="&#xf15c;" d="M819 584q8-7 16-20h-264v264q13-8 21-16z m-265-91h303v-589q0-23-15-38t-38-16h-750q-23 0-38 16t-16 38v892q0 23 16 38t38 16h446v-304q0-22 16-37t38-16z m89-411v36q0 8-5 13t-13 5h-393q-8 0-13-5t-5-13v-36q0-8 5-13t13-5h393q8 0 13 5t5 13z m0 143v36q0 8-5 13t-13 5h-393q-8 0-13-5t-5-13v-36q0-8 5-13t13-5h393q8 0 13 5t5 13z m0 143v36q0 7-5 12t-13 5h-393q-8 0-13-5t-5-12v-36q0-8 5-13t13-5h393q8 0 13 5t5 13z" horiz-adv-x="857.1" />
123 <glyph glyph-name="plus-squared-alt" unicode="&#xf196;" d="M643 404v-36q0-8-5-13t-13-5h-196v-196q0-8-5-13t-13-5h-36q-8 0-13 5t-5 13v196h-196q-8 0-13 5t-5 13v36q0 7 5 12t13 5h196v197q0 8 5 13t13 5h36q8 0 13-5t5-13v-197h196q8 0 13-5t5-12z m71-250v464q0 37-26 63t-63 26h-464q-37 0-63-26t-27-63v-464q0-37 27-63t63-27h464q37 0 63 27t26 63z m72 464v-464q0-67-47-114t-114-47h-464q-67 0-114 47t-47 114v464q0 66 47 113t114 48h464q66 0 114-48t47-113z" horiz-adv-x="785.7" />
74 124
75 125 <glyph glyph-name="file-code" unicode="&#xf1c9;" d="M819 638q16-16 27-42t11-50v-642q0-23-15-38t-38-16h-750q-23 0-38 16t-16 38v892q0 23 16 38t38 16h500q22 0 49-11t42-27z m-248 136v-210h210q-5 17-12 23l-175 175q-6 7-23 12z m215-853v572h-232q-23 0-38 16t-16 37v233h-429v-858h715z m-518 500q4 7 12 7t13-3l28-21q7-5 7-12t-3-13l-102-136 102-136q4-6 3-13t-7-12l-28-21q-6-4-13-4t-12 7l-126 168q-8 11 0 22z m447-167q8-11 0-22l-126-168q-4-6-11-7t-14 4l-28 21q-6 5-7 12t3 13l102 136-102 136q-4 6-3 13t7 12l28 21q6 4 14 3t11-7z m-346-258q-7 1-11 8t-3 13l77 464q1 7 7 11t14 3l35-5q7-2 11-8t3-13l-77-464q-1-7-7-11t-13-3z" horiz-adv-x="857.1" />
126
127 <glyph glyph-name="history" unicode="&#xf1da;" d="M857 350q0-87-34-166t-91-137-137-92-166-34q-96 0-183 41t-147 114q-4 6-4 13t5 11l76 77q6 5 14 5 9-1 13-7 41-53 100-82t126-29q58 0 110 23t92 61 61 91 22 111-22 111-61 91-92 61-110 23q-55 0-105-20t-90-57l77-77q17-16 8-38-10-23-33-23h-250q-15 0-25 11t-11 25v250q0 24 22 33 22 10 39-8l72-72q60 57 137 88t159 31q87 0 166-34t137-92 91-137 34-166z m-357 161v-250q0-8-5-13t-13-5h-178q-8 0-13 5t-5 13v35q0 8 5 13t13 5h125v197q0 8 5 13t12 5h36q8 0 13-5t5-13z" horiz-adv-x="857.1" />
128
129 <glyph glyph-name="sliders" unicode="&#xf1de;" d="M196 64v-71h-196v71h196z m197 72q14 0 25-11t11-25v-143q0-14-11-25t-25-11h-143q-14 0-25 11t-11 25v143q0 15 11 25t25 11h143z m89 214v-71h-482v71h482z m-357 286v-72h-125v72h125z m732-572v-71h-411v71h411z m-536 643q15 0 26-10t10-26v-142q0-15-10-25t-26-11h-142q-15 0-25 11t-11 25v142q0 15 11 26t25 10h142z m358-286q14 0 25-10t10-25v-143q0-15-10-25t-25-11h-143q-15 0-25 11t-11 25v143q0 14 11 25t25 10h143z m178-71v-71h-125v71h125z m0 286v-72h-482v72h482z" horiz-adv-x="857.1" />
130
131 <glyph glyph-name="trash" unicode="&#xf1f8;" d="M286 82v393q0 8-5 13t-13 5h-36q-8 0-13-5t-5-13v-393q0-8 5-13t13-5h36q8 0 13 5t5 13z m143 0v393q0 8-5 13t-13 5h-36q-8 0-13-5t-5-13v-393q0-8 5-13t13-5h36q8 0 13 5t5 13z m142 0v393q0 8-5 13t-12 5h-36q-8 0-13-5t-5-13v-393q0-8 5-13t13-5h36q7 0 12 5t5 13z m-303 554h250l-27 65q-4 5-9 6h-177q-6-1-10-6z m518-18v-36q0-8-5-13t-13-5h-54v-529q0-46-26-80t-63-34h-464q-37 0-63 33t-27 79v531h-53q-8 0-13 5t-5 13v36q0 8 5 13t13 5h172l39 93q9 21 31 35t44 15h178q23 0 44-15t30-35l39-93h173q8 0 13-5t5-13z" horiz-adv-x="785.7" />
76 132 </font>
77 133 </defs>
78 134 </svg> No newline at end of file
1 NO CONTENT: modified file, binary diff hidden
1 NO CONTENT: modified file, binary diff hidden
1 NO CONTENT: modified file, binary diff hidden
1 NO CONTENT: file renamed from rhodecode/public/images/rhodecode-logo-white-216x60.png to rhodecode/public/images/rhodecode-logo-white-60x60.png, binary diff hidden
@@ -98,7 +98,7 b' function setRCMouseBindings(repoName, re'
98 98 });
99 99 Mousetrap.bind(['g c'], function(e) {
100 100 window.location = pyroutes.url(
101 'repo_changelog', {'repo_name': repoName});
101 'repo_commits', {'repo_name': repoName});
102 102 });
103 103 Mousetrap.bind(['g F'], function(e) {
104 104 window.location = pyroutes.url(
@@ -131,6 +131,7 b' function registerRCRoutes() {'
131 131 pyroutes.register('repo_new', '/_admin/repos/new', []);
132 132 pyroutes.register('repo_create', '/_admin/repos/create', []);
133 133 pyroutes.register('repo_groups', '/_admin/repo_groups', []);
134 pyroutes.register('repo_groups_data', '/_admin/repo_groups_data', []);
134 135 pyroutes.register('repo_group_new', '/_admin/repo_group/new', []);
135 136 pyroutes.register('repo_group_create', '/_admin/repo_group/create', []);
136 137 pyroutes.register('channelstream_connect', '/_admin/channelstream/connect', []);
@@ -148,6 +149,7 b' function registerRCRoutes() {'
148 149 pyroutes.register('repo_group_list_data', '/_repo_groups', []);
149 150 pyroutes.register('goto_switcher_data', '/_goto_data', []);
150 151 pyroutes.register('markup_preview', '/_markup_preview', []);
152 pyroutes.register('file_preview', '/_file_preview', []);
151 153 pyroutes.register('store_user_session_value', '/_store_session_attr', []);
152 154 pyroutes.register('journal', '/_admin/journal', []);
153 155 pyroutes.register('journal_rss', '/_admin/journal/rss', []);
@@ -195,14 +197,17 b' function registerRCRoutes() {'
195 197 pyroutes.register('repo_files_edit_file', '/%(repo_name)s/edit_file/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
196 198 pyroutes.register('repo_files_update_file', '/%(repo_name)s/update_file/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
197 199 pyroutes.register('repo_files_add_file', '/%(repo_name)s/add_file/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
200 pyroutes.register('repo_files_upload_file', '/%(repo_name)s/upload_file/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
198 201 pyroutes.register('repo_files_create_file', '/%(repo_name)s/create_file/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
199 202 pyroutes.register('repo_refs_data', '/%(repo_name)s/refs-data', ['repo_name']);
200 203 pyroutes.register('repo_refs_changelog_data', '/%(repo_name)s/refs-data-changelog', ['repo_name']);
201 204 pyroutes.register('repo_stats', '/%(repo_name)s/repo_stats/%(commit_id)s', ['repo_name', 'commit_id']);
205 pyroutes.register('repo_commits', '/%(repo_name)s/commits', ['repo_name']);
206 pyroutes.register('repo_commits_file', '/%(repo_name)s/commits/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
207 pyroutes.register('repo_commits_elements', '/%(repo_name)s/commits_elements', ['repo_name']);
208 pyroutes.register('repo_commits_elements_file', '/%(repo_name)s/commits_elements/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
202 209 pyroutes.register('repo_changelog', '/%(repo_name)s/changelog', ['repo_name']);
203 210 pyroutes.register('repo_changelog_file', '/%(repo_name)s/changelog/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
204 pyroutes.register('repo_changelog_elements', '/%(repo_name)s/changelog_elements', ['repo_name']);
205 pyroutes.register('repo_changelog_elements_file', '/%(repo_name)s/changelog_elements/%(commit_id)s/%(f_path)s', ['repo_name', 'commit_id', 'f_path']);
206 211 pyroutes.register('repo_compare_select', '/%(repo_name)s/compare', ['repo_name']);
207 212 pyroutes.register('repo_compare', '/%(repo_name)s/compare/%(source_ref_type)s@%(source_ref)s...%(target_ref_type)s@%(target_ref)s', ['repo_name', 'source_ref_type', 'source_ref', 'target_ref_type', 'target_ref']);
208 213 pyroutes.register('tags_home', '/%(repo_name)s/tags', ['repo_name']);
@@ -356,6 +361,12 b' function registerRCRoutes() {'
356 361 pyroutes.register('my_account_auth_tokens_add', '/_admin/my_account/auth_tokens/new', []);
357 362 pyroutes.register('my_account_external_identity', '/_admin/my_account/external-identity', []);
358 363 pyroutes.register('my_account_external_identity_delete', '/_admin/my_account/external-identity/delete', []);
364 pyroutes.register('repo_artifacts_list', '/%(repo_name)s/artifacts', ['repo_name']);
365 pyroutes.register('repo_artifacts_data', '/%(repo_name)s/artifacts_data', ['repo_name']);
366 pyroutes.register('repo_artifacts_new', '/%(repo_name)s/artifacts/new', ['repo_name']);
367 pyroutes.register('repo_artifacts_get', '/%(repo_name)s/artifacts/download/%(uid)s', ['repo_name', 'uid']);
368 pyroutes.register('repo_artifacts_store', '/%(repo_name)s/artifacts/store', ['repo_name']);
369 pyroutes.register('repo_artifacts_delete', '/%(repo_name)s/artifacts/delete/%(uid)s', ['repo_name', 'uid']);
359 370 pyroutes.register('repo_automation', '/%(repo_name)s/settings/automation', ['repo_name']);
360 371 pyroutes.register('repo_automation_update', '/%(repo_name)s/settings/automation/%(entry_id)s/update', ['repo_name', 'entry_id']);
361 372 pyroutes.register('edit_repo_remote_push', '/%(repo_name)s/settings/remote/push', ['repo_name']);
@@ -528,7 +528,19 b''
528 528 if ($.isFunction(serviceUrl)) {
529 529 serviceUrl = serviceUrl.call(that.element, query);
530 530 }
531 cacheKey = serviceUrl + '?' + $.param(params || {});
531
532 var callParams = {};
533 //make an evaluated copy of params
534 $.each(params, function(index, value) {
535 if($.isFunction(value)){
536 callParams[index] = value();
537 }
538 else {
539 callParams[index] = value;
540 }
541 });
542
543 cacheKey = serviceUrl + '?' + $.param(callParams);
532 544 response = that.cachedResponse[cacheKey];
533 545 }
534 546
@@ -536,7 +548,7 b''
536 548 that.suggestions = response.suggestions;
537 549 that.suggest();
538 550 } else if (!that.isBadQuery(query)) {
539 if (options.onSearchStart.call(that.element, options.params) === false) {
551 if (options.onSearchStart.call(that.element, params) === false) {
540 552 return;
541 553 }
542 554 if (that.currentRequest) {
@@ -102,7 +102,7 b' var showRepoStats = function(target, dat'
102 102 var total = 0;
103 103 var no_data = true;
104 104 var tbl = document.createElement('table');
105 tbl.setAttribute('class', 'trending_language_tbl');
105 tbl.setAttribute('class', 'trending_language_tbl rctable');
106 106
107 107 $.each(data, function(key, val){
108 108 total += val.count;
@@ -120,54 +120,47 b' var showRepoStats = function(target, dat'
120 120 cnt += 1;
121 121 no_data = false;
122 122
123 var hide = cnt > 2;
124 123 var tr = document.createElement('tr');
125 if (hide) {
126 tr.setAttribute('style', 'display:none');
127 tr.setAttribute('class', 'stats_hidden');
128 }
129 124
130 125 var key = val[0];
131 126 var obj = {"desc": val[1].desc, "count": val[1].count};
132 127
133 var percentage = Math.round((obj.count / total * 100), 2);
134
128 // meta language names
135 129 var td1 = document.createElement('td');
136 td1.width = 300;
137 130 var trending_language_label = document.createElement('div');
138 trending_language_label.innerHTML = obj.desc + " (.{0})".format(key);
131 trending_language_label.innerHTML = obj.desc;
139 132 td1.appendChild(trending_language_label);
140 133
134 // extensions
141 135 var td2 = document.createElement('td');
142 var trending_language = document.createElement('div');
143 var nr_files = obj.count +" "+ _ngettext('file', 'files', obj.count);
144
145 trending_language.title = key + " " + nr_files;
136 var extension = document.createElement('div');
137 extension.innerHTML = ".{0}".format(key)
138 td2.appendChild(extension);
146 139
147 trending_language.innerHTML = "<span>" + percentage + "% " + nr_files
148 + "</span><b>" + percentage + "% " + nr_files + "</b>";
140 // number of files
141 var td3 = document.createElement('td');
142 var file_count = document.createElement('div');
143 var percentage_num = Math.round((obj.count / total * 100), 2);
144 var label = _ngettext('file', 'files', obj.count);
145 file_count.innerHTML = "{0} {1} ({2}%)".format(obj.count, label, percentage_num) ;
146 td3.appendChild(file_count);
149 147
150 trending_language.setAttribute("class", 'trending_language');
151 $('b', trending_language)[0].style.width = percentage + "%";
152 td2.appendChild(trending_language);
148 // percentage
149 var td4 = document.createElement('td');
150 td4.setAttribute("class", 'trending_language');
151
152 var percentage = document.createElement('div');
153 percentage.setAttribute('class', 'lang-bar');
154 percentage.innerHTML = "&nbsp;";
155 percentage.style.width = percentage_num + '%';
156 td4.appendChild(percentage);
153 157
154 158 tr.appendChild(td1);
155 159 tr.appendChild(td2);
160 tr.appendChild(td3);
161 tr.appendChild(td4);
156 162 tbl.appendChild(tr);
157 if (cnt == 3) {
158 var show_more = document.createElement('tr');
159 var td = document.createElement('td');
160 lnk = document.createElement('a');
161 163
162 lnk.href = '#';
163 lnk.innerHTML = _gettext('Show more');
164 lnk.id = 'code_stats_show_more';
165 td.appendChild(lnk);
166
167 show_more.appendChild(td);
168 show_more.appendChild(document.createElement('td'));
169 tbl.appendChild(show_more);
170 }
171 164 });
172 165
173 166 $(container).html(tbl);
@@ -46,6 +46,8 b' var CommitsController = function () {'
46 46 self.$graphCanvas.html('');
47 47
48 48 var edgeData = $("[data-graph]").data('graph') || this.$graphCanvas.data('graph') || [];
49 var prev_link = $('.load-more-commits').find('.prev-commits').get(0);
50 var next_link = $('.load-more-commits').find('.next-commits').get(0);
49 51
50 52 // Determine max number of edges per row in graph
51 53 var edgeCount = 1;
@@ -57,10 +59,20 b' var CommitsController = function () {'
57 59 });
58 60 });
59 61
62 if (prev_link && next_link) {
63 var graph_padding = -64;
64 }
65 else if (next_link) {
66 var graph_padding = -32;
67 } else {
68 var graph_padding = 0;
69 }
70
60 71 var x_step = Math.min(10, Math.floor(86 / edgeCount));
72 var height = $('#changesets').find('.commits-range').height() + graph_padding;
61 73 var graph_options = {
62 74 width: 100,
63 height: $('#changesets').find('.commits-range').height(),
75 height: height,
64 76 x_step: x_step,
65 77 y_step: 42,
66 78 dotRadius: 3.5,
@@ -85,13 +97,20 b' var CommitsController = function () {'
85 97 this.$graphCanvas.commits(graph_options);
86 98
87 99 this.setLabelText(edgeData);
88 if ($('.load-more-commits').find('.prev-commits').get(0)) {
89 var padding = 75;
90 100
91 } else {
92 var padding = 43;
101 var padding = 90;
102 if (prev_link) {
103 padding += 34;
104
93 105 }
94 106 $('#graph_nodes').css({'padding-top': padding});
107
108 $.each($('.message.truncate'), function(idx, value) {
109 if(!(value.offsetWidth < value.scrollWidth)){
110 $(this).closest('td').siblings('.expand_commit').find('i').hide();
111 }
112 });
113
95 114 };
96 115
97 116 this.getChunkUrl = function (page, chunk, branch, commit_id, f_path) {
@@ -112,10 +131,10 b' var CommitsController = function () {'
112 131 }
113 132
114 133 if (urlData['commit_id'] && urlData['f_path']) {
115 return pyroutes.url('repo_changelog_elements_file', urlData);
134 return pyroutes.url('repo_commits_elements_file', urlData);
116 135 }
117 136 else {
118 return pyroutes.url('repo_changelog_elements', urlData);
137 return pyroutes.url('repo_commits_elements', urlData);
119 138 }
120 139
121 140 };
@@ -204,7 +204,12 b' var CodeMirrorCompleteAfter = function(c'
204 204 };
205 205
206 206 var initCodeMirror = function(textAreadId, resetUrl, focus, options) {
207 var ta = $('#' + textAreadId).get(0);
207 if (textAreadId.substr(0,1) === "#"){
208 var ta = $(textAreadId).get(0);
209 }else {
210 var ta = $('#' + textAreadId).get(0);
211 }
212
208 213 if (focus === undefined) {
209 214 focus = true;
210 215 }
@@ -644,18 +649,6 b' var fillCodeMirrorOptions = function(tar'
644 649 }
645 650 };
646 651
647 var CodeMirrorPreviewEnable = function(edit_mode) {
648 // in case it a preview enabled mode enable the button
649 if (['markdown', 'rst', 'gfm'].indexOf(edit_mode) !== -1) {
650 $('#render_preview').removeClass('hidden');
651 }
652 else {
653 if (!$('#render_preview').hasClass('hidden')) {
654 $('#render_preview').addClass('hidden');
655 }
656 }
657 };
658
659 652
660 653 /* markup form */
661 654 (function(mod) {
@@ -587,12 +587,14 b' var CommentsController = function() {'
587 587 $('#content').removeClass("wrapper");
588 588 $('#content').addClass("wide-mode-wrapper");
589 589 $(node).addClass('btn-success');
590 return true
590 591 } else {
591 592 $('#content').removeClass("wide-mode-wrapper");
592 593 $('#content').addClass("wrapper");
593 594 $(node).removeClass('btn-success');
595 return false
594 596 }
595 return false;
597
596 598 };
597 599
598 600 this.toggleComments = function(node, show) {
This diff has been collapsed as it changes many lines, (627 lines changed) Show them Hide them
@@ -19,234 +19,254 b''
19 19 /**
20 20 * Search file list
21 21 */
22 // global reference to file-node filter
23 var _NODEFILTER = {};
22
23 var NodeFilter = {};
24 24
25 var fileBrowserListeners = function(node_list_url, url_base){
26 var n_filter = $('#node_filter').get(0);
27
28 _NODEFILTER.filterTimeout = null;
29 var nodes = null;
25 var fileBrowserListeners = function (node_list_url, url_base) {
26 var $filterInput = $('#node_filter');
27 var n_filter = $filterInput.get(0);
30 28
31 _NODEFILTER.fetchNodes = function(callback) {
32 $.ajax({url: node_list_url, headers: {'X-PARTIAL-XHR': true}})
33 .done(function(data){
34 nodes = data.nodes;
35 if (callback) {
36 callback();
37 }
38 })
39 .fail(function(data){
40 console.log('failed to load');
41 });
42 };
29 NodeFilter.filterTimeout = null;
30 var nodes = null;
43 31
44 _NODEFILTER.fetchNodesCallback = function() {
45 $('#node_filter_box_loading').hide();
46 $('#node_filter_box').removeClass('hidden').show();
47 n_filter.focus();
48 if ($('#node_filter').hasClass('init')){
49 n_filter.value = '';
50 $('#node_filter').removeClass('init');
51 }
52 };
32 NodeFilter.focus = function () {
33 $filterInput.focus()
34 };
53 35
54 _NODEFILTER.initFilter = function(){
55 $('#node_filter_box_loading').removeClass('hidden').show();
56 $('#search_activate_id').hide();
57 $('#search_deactivate_id').removeClass('hidden').show();
58 $('#add_node_id').hide();
59 _NODEFILTER.fetchNodes(_NODEFILTER.fetchNodesCallback);
60 };
36 NodeFilter.fetchNodes = function (callback) {
37 $.ajax(
38 {url: node_list_url, headers: {'X-PARTIAL-XHR': true}})
39 .done(function (data) {
40 nodes = data.nodes;
41 if (callback) {
42 callback();
43 }
44 })
45 .fail(function (data) {
46 console.log('failed to load');
47 });
48 };
61 49
62 _NODEFILTER.resetFilter = function(){
63 $('#node_filter_box_loading').hide();
64 $('#node_filter_box').hide();
65 $('#search_activate_id').show();
66 $('#search_deactivate_id').hide();
67 $('#add_node_id').show();
68 $('#tbody').show();
69 $('#tbody_filtered').hide();
70 $('#node_filter').val('');
71 };
72
73 _NODEFILTER.fuzzy_match = function(filepath, query) {
74 var highlight = [];
75 var order = 0;
76 for (var i = 0; i < query.length; i++) {
77 var match_position = filepath.indexOf(query[i]);
78 if (match_position !== -1) {
79 var prev_match_position = highlight[highlight.length-1];
80 if (prev_match_position === undefined) {
81 highlight.push(match_position);
82 } else {
83 var current_match_position = prev_match_position + match_position + 1;
84 highlight.push(current_match_position);
85 order = order + current_match_position - prev_match_position;
50 NodeFilter.initFilter = function (e) {
51 if ($filterInput.hasClass('loading')) {
52 return
86 53 }
87 filepath = filepath.substring(match_position+1);
88 } else {
89 return false;
90 }
91 }
92 return {'order': order,
93 'highlight': highlight};
94 };
95 54
96 _NODEFILTER.sortPredicate = function(a, b) {
97 if (a.order < b.order) return -1;
98 if (a.order > b.order) return 1;
99 if (a.filepath < b.filepath) return -1;
100 if (a.filepath > b.filepath) return 1;
101 return 0;
102 };
103
104 _NODEFILTER.updateFilter = function(elem, e) {
105 return function(){
106 // Reset timeout
107 _NODEFILTER.filterTimeout = null;
108 var query = elem.value.toLowerCase();
109 var match = [];
110 var matches_max = 20;
111 if (query !== ""){
112 var results = [];
113 for(var k=0;k<nodes.length;k++){
114 var result = _NODEFILTER.fuzzy_match(
115 nodes[k].name.toLowerCase(), query);
116 if (result) {
117 result.type = nodes[k].type;
118 result.filepath = nodes[k].name;
119 results.push(result);
120 }
121 }
122 results = results.sort(_NODEFILTER.sortPredicate);
123 var limit = matches_max;
124 if (results.length < matches_max) {
125 limit = results.length;
55 // in case we are already loaded, do nothing
56 if (!$filterInput.hasClass('init')) {
57 return NodeFilter.handleKey(e);
126 58 }
127 for (var i=0; i<limit; i++){
128 if(query && results.length > 0){
129 var n = results[i].filepath;
130 var t = results[i].type;
131 var n_hl = n.split("");
132 var pos = results[i].highlight;
133 for (var j = 0; j < pos.length; j++) {
134 n_hl[pos[j]] = "<em>" + n_hl[pos[j]] + "</em>";
135 }
136 n_hl = n_hl.join("");
137 var new_url = url_base.replace('__FPATH__',n);
59 var iconLoading = 'icon-spin animate-spin';
60 var iconSearch = 'icon-search';
61 $('.files-filter-box-path i').removeClass(iconSearch).addClass(iconLoading);
62 $filterInput.addClass('loading');
138 63
139 var typeObj = {
140 dir: 'icon-directory browser-dir',
141 file: 'icon-file-text browser-file'
142 };
64 var callback = function (org) {
65 return function () {
66 if ($filterInput.hasClass('init')) {
67 $filterInput.removeClass('init');
68 $filterInput.removeClass('loading');
69 }
70 $('.files-filter-box-path i').removeClass(iconLoading).addClass(iconSearch);
143 71
144 var typeIcon = '<i class="{0}"></i>'.format(typeObj[t]);
145 match.push('<tr class="browser-result"><td><a class="pjax-link" href="{0}">{1}{2}</a></td><td colspan="5"></td></tr>'.format(new_url,typeIcon, n_hl));
146 }
147 }
148 if(results.length > limit){
149 var truncated_count = results.length - matches_max;
150 if (truncated_count === 1) {
151 match.push('<tr><td>{0} {1}</td><td colspan="5"></td></tr>'.format(truncated_count, _gettext('truncated result')));
152 } else {
153 match.push('<tr><td>{0} {1}</td><td colspan="5"></td></tr>'.format(truncated_count, _gettext('truncated results')));
154 }
155 }
156 }
157 if (query !== ""){
158 $('#tbody').hide();
159 $('#tbody_filtered').show();
72 // auto re-filter if we filled in the input
73 if (n_filter.value !== "") {
74 NodeFilter.updateFilter(n_filter, e)()
75 }
160 76
161 if (match.length === 0){
162 match.push('<tr><td>{0}</td><td colspan="5"></td></tr>'.format(_gettext('No matching files')));
163 }
164 $('#tbody_filtered').html(match.join(""));
165 }
166 else{
77 }
78 };
79 // load node data
80 NodeFilter.fetchNodes(callback());
81
82 };
83
84 NodeFilter.resetFilter = function () {
167 85 $('#tbody').show();
168 86 $('#tbody_filtered').hide();
169 }
87 $filterInput.val('');
88 };
89
90 NodeFilter.handleKey = function (e) {
91 var scrollDown = function (element) {
92 var elementBottom = element.offset().top + $(element).outerHeight();
93 var windowBottom = window.innerHeight + $(window).scrollTop();
94 if (elementBottom > windowBottom) {
95 var offset = elementBottom - window.innerHeight;
96 $('html,body').scrollTop(offset);
97 return false;
98 }
99 return true;
100 };
101
102 var scrollUp = function (element) {
103 if (element.offset().top < $(window).scrollTop()) {
104 $('html,body').scrollTop(element.offset().top);
105 return false;
106 }
107 return true;
108 };
109 var $hlElem = $('.browser-highlight');
110
111 if (e.keyCode === 40) { // Down
112 if ($hlElem.length === 0) {
113 $('.browser-result').first().addClass('browser-highlight');
114 } else {
115 var next = $hlElem.next();
116 if (next.length !== 0) {
117 $hlElem.removeClass('browser-highlight');
118 next.addClass('browser-highlight');
119 }
120 }
121
122 if ($hlElem.get(0) !== undefined){
123 scrollDown($hlElem);
124 }
125 }
126 if (e.keyCode === 38) { // Up
127 e.preventDefault();
128 if ($hlElem.length !== 0) {
129 var next = $hlElem.prev();
130 if (next.length !== 0) {
131 $('.browser-highlight').removeClass('browser-highlight');
132 next.addClass('browser-highlight');
133 }
134 }
135
136 if ($hlElem.get(0) !== undefined){
137 scrollUp($hlElem);
138 }
139
140 }
141 if (e.keyCode === 13) { // Enter
142 if ($('.browser-highlight').length !== 0) {
143 var url = $('.browser-highlight').find('.match-link').attr('href');
144 window.location = url;
145 }
146 }
147 if (e.keyCode === 27) { // Esc
148 NodeFilter.resetFilter();
149 $('html,body').scrollTop(0);
150 }
151
152 var capture_keys = [
153 40, // ArrowDown
154 38, // ArrowUp
155 39, // ArrowRight
156 37, // ArrowLeft
157 13, // Enter
158 27 // Esc
159 ];
160
161 if ($.inArray(e.keyCode, capture_keys) === -1) {
162 clearTimeout(NodeFilter.filterTimeout);
163 NodeFilter.filterTimeout = setTimeout(NodeFilter.updateFilter(n_filter, e), 200);
164 }
170 165
171 166 };
172 };
173
174 var scrollDown = function(element){
175 var elementBottom = element.offset().top + $(element).outerHeight();
176 var windowBottom = window.innerHeight + $(window).scrollTop();
177 if (elementBottom > windowBottom) {
178 var offset = elementBottom - window.innerHeight;
179 $('html,body').scrollTop(offset);
180 return false;
181 }
182 return true;
183 };
184 167
185 var scrollUp = function(element){
186 if (element.offset().top < $(window).scrollTop()) {
187 $('html,body').scrollTop(element.offset().top);
188 return false;
189 }
190 return true;
191 };
168 NodeFilter.fuzzy_match = function (filepath, query) {
169 var highlight = [];
170 var order = 0;
171 for (var i = 0; i < query.length; i++) {
172 var match_position = filepath.indexOf(query[i]);
173 if (match_position !== -1) {
174 var prev_match_position = highlight[highlight.length - 1];
175 if (prev_match_position === undefined) {
176 highlight.push(match_position);
177 } else {
178 var current_match_position = prev_match_position + match_position + 1;
179 highlight.push(current_match_position);
180 order = order + current_match_position - prev_match_position;
181 }
182 filepath = filepath.substring(match_position + 1);
183 } else {
184 return false;
185 }
186 }
187 return {
188 'order': order,
189 'highlight': highlight
190 };
191 };
192 192
193 $('#filter_activate').click(function() {
194 _NODEFILTER.initFilter();
195 });
196
197 $('#filter_deactivate').click(function() {
198 _NODEFILTER.resetFilter();
199 });
200
201 $(n_filter).click(function() {
202 if ($('#node_filter').hasClass('init')){
203 n_filter.value = '';
204 $('#node_filter').removeClass('init');
205 }
206 });
193 NodeFilter.sortPredicate = function (a, b) {
194 if (a.order < b.order) return -1;
195 if (a.order > b.order) return 1;
196 if (a.filepath < b.filepath) return -1;
197 if (a.filepath > b.filepath) return 1;
198 return 0;
199 };
207 200
208 $(n_filter).keydown(function(e) {
209 if (e.keyCode === 40){ // Down
210 if ($('.browser-highlight').length === 0){
211 $('.browser-result').first().addClass('browser-highlight');
212 } else {
213 var next = $('.browser-highlight').next();
214 if (next.length !== 0) {
215 $('.browser-highlight').removeClass('browser-highlight');
216 next.addClass('browser-highlight');
217 }
218 }
219 scrollDown($('.browser-highlight'));
220 }
221 if (e.keyCode === 38){ // Up
222 e.preventDefault();
223 if ($('.browser-highlight').length !== 0){
224 var next = $('.browser-highlight').prev();
225 if (next.length !== 0) {
226 $('.browser-highlight').removeClass('browser-highlight');
227 next.addClass('browser-highlight');
228 }
229 }
230 scrollUp($('.browser-highlight'));
231 }
232 if (e.keyCode === 13){ // Enter
233 if ($('.browser-highlight').length !== 0){
234 var url = $('.browser-highlight').find('.pjax-link').attr('href');
235 $.pjax({url: url, container: '#pjax-container', timeout: pjaxTimeout});
236 }
237 }
238 if (e.keyCode === 27){ // Esc
239 _NODEFILTER.resetFilter();
240 $('html,body').scrollTop(0);
241 }
242 });
243 var capture_keys = [40, 38, 39, 37, 13, 27];
244 $(n_filter).keyup(function(e) {
245 if ($.inArray(e.keyCode, capture_keys) === -1){
246 clearTimeout(_NODEFILTER.filterTimeout);
247 _NODEFILTER.filterTimeout = setTimeout(_NODEFILTER.updateFilter(n_filter, e),200);
248 }
249 });
201 NodeFilter.updateFilter = function (elem, e) {
202 return function () {
203 // Reset timeout
204 NodeFilter.filterTimeout = null;
205 var query = elem.value.toLowerCase();
206 var match = [];
207 var matches_max = 20;
208 if (query !== "") {
209 var results = [];
210 for (var k = 0; k < nodes.length; k++) {
211 var result = NodeFilter.fuzzy_match(
212 nodes[k].name.toLowerCase(), query);
213 if (result) {
214 result.type = nodes[k].type;
215 result.filepath = nodes[k].name;
216 results.push(result);
217 }
218 }
219 results = results.sort(NodeFilter.sortPredicate);
220 var limit = matches_max;
221 if (results.length < matches_max) {
222 limit = results.length;
223 }
224 for (var i = 0; i < limit; i++) {
225 if (query && results.length > 0) {
226 var n = results[i].filepath;
227 var t = results[i].type;
228 var n_hl = n.split("");
229 var pos = results[i].highlight;
230 for (var j = 0; j < pos.length; j++) {
231 n_hl[pos[j]] = "<em>" + n_hl[pos[j]] + "</em>";
232 }
233 n_hl = n_hl.join("");
234 var new_url = url_base.replace('__FPATH__', n);
235
236 var typeObj = {
237 dir: 'icon-directory browser-dir',
238 file: 'icon-file-text browser-file'
239 };
240
241 var typeIcon = '<i class="{0}"></i>'.format(typeObj[t]);
242 match.push('<tr class="browser-result"><td><a class="match-link" href="{0}">{1}{2}</a></td><td colspan="5"></td></tr>'.format(new_url, typeIcon, n_hl));
243 }
244 }
245 if (results.length > limit) {
246 var truncated_count = results.length - matches_max;
247 if (truncated_count === 1) {
248 match.push('<tr><td>{0} {1}</td><td colspan="5"></td></tr>'.format(truncated_count, _gettext('truncated result')));
249 } else {
250 match.push('<tr><td>{0} {1}</td><td colspan="5"></td></tr>'.format(truncated_count, _gettext('truncated results')));
251 }
252 }
253 }
254 if (query !== "") {
255 $('#tbody').hide();
256 $('#tbody_filtered').show();
257
258 if (match.length === 0) {
259 match.push('<tr><td>{0}</td><td colspan="5"></td></tr>'.format(_gettext('No matching files')));
260 }
261 $('#tbody_filtered').html(match.join(""));
262 } else {
263 $('#tbody').show();
264 $('#tbody_filtered').hide();
265 }
266
267 };
268 };
269
250 270 };
251 271
252 272 var getIdentNode = function(n){
@@ -308,3 +328,190 b' var getSelectionLink = function(e) {'
308 328 }
309 329 }
310 330 };
331
332 var getFileState = function() {
333 // relies on a global set filesUrlData
334 var f_path = filesUrlData['f_path'];
335 var commit_id = filesUrlData['commit_id'];
336
337 var url_params = {
338 repo_name: templateContext.repo_name,
339 commit_id: commit_id,
340 f_path:'__FPATH__'
341 };
342 if (atRef !== '') {
343 url_params['at'] = atRef
344 }
345
346 var _url_base = pyroutes.url('repo_files', url_params);
347 var _node_list_url = pyroutes.url('repo_files_nodelist',
348 {repo_name: templateContext.repo_name,
349 commit_id: commit_id, f_path: f_path});
350
351 return {
352 f_path: f_path,
353 commit_id: commit_id,
354 node_list_url: _node_list_url,
355 url_base: _url_base
356 };
357 };
358
359 var getFilesMetadata = function() {
360 // relies on metadataRequest global state
361 if (metadataRequest && metadataRequest.readyState != 4) {
362 metadataRequest.abort();
363 }
364
365 if ($('#file-tree-wrapper').hasClass('full-load')) {
366 // in case our HTML wrapper has full-load class we don't
367 // trigger the async load of metadata
368 return false;
369 }
370
371 var state = getFileState();
372 var url_data = {
373 'repo_name': templateContext.repo_name,
374 'commit_id': state.commit_id,
375 'f_path': state.f_path
376 };
377
378 var url = pyroutes.url('repo_nodetree_full', url_data);
379
380 metadataRequest = $.ajax({url: url});
381
382 metadataRequest.done(function(data) {
383 $('#file-tree').html(data);
384 timeagoActivate();
385 });
386 metadataRequest.fail(function (data, textStatus, errorThrown) {
387 if (data.status != 0) {
388 alert("Error while fetching metadata.\nError code {0} ({1}).Please consider reloading the page".format(data.status,data.statusText));
389 }
390 });
391 };
392
393 // show more authors
394 var showAuthors = function(elem, annotate) {
395 var state = getFileState('callbacks');
396
397 var url = pyroutes.url('repo_file_authors',
398 {'repo_name': templateContext.repo_name,
399 'commit_id': state.commit_id, 'f_path': state.f_path});
400
401 $.pjax({
402 url: url,
403 data: 'annotate={0}'.format(annotate),
404 container: '#file_authors',
405 push: false,
406 timeout: 5000
407 }).complete(function(){
408 $(elem).hide();
409 $('#file_authors_title').html(_gettext('All Authors'))
410 })
411 };
412
413
414 (function (mod) {
415
416 if (typeof exports == "object" && typeof module == "object") {
417 // CommonJS
418 module.exports = mod();
419 } else {
420 // Plain browser env
421 (this || window).FileEditor = mod();
422 }
423
424 })(function () {
425 "use strict";
426
427 function FileEditor(textAreaElement, options) {
428 if (!(this instanceof FileEditor)) {
429 return new FileEditor(textAreaElement, options);
430 }
431 // bind the element instance to our Form
432 var te = $(textAreaElement).get(0);
433 if (te !== undefined) {
434 te.FileEditor = this;
435 }
436
437 this.modes_select = '#set_mode';
438 this.filename_selector = '#filename';
439 this.commit_btn_selector = '#commit_btn';
440 this.line_wrap_selector = '#line_wrap';
441 this.editor_preview_selector = '#editor_preview';
442
443 if (te !== undefined) {
444 this.cm = initCodeMirror(textAreaElement, null, false);
445 }
446
447 // FUNCTIONS and helpers
448 var self = this;
449
450 this.submitHandler = function() {
451 $(self.commit_btn_selector).on('click', function(e) {
452
453 var filename = $(self.filename_selector).val();
454 if (filename === "") {
455 alert("Missing filename");
456 e.preventDefault();
457 }
458
459 var button = $(this);
460 if (button.hasClass('clicked')) {
461 button.attr('disabled', true);
462 } else {
463 button.addClass('clicked');
464 }
465 });
466 };
467 this.submitHandler();
468
469 // on select line wraps change the editor
470 this.lineWrapHandler = function () {
471 $(self.line_wrap_selector).on('change', function (e) {
472 var selected = e.currentTarget;
473 var line_wraps = {'on': true, 'off': false}[selected.value];
474 setCodeMirrorLineWrap(self.cm, line_wraps)
475 });
476 };
477 this.lineWrapHandler();
478
479
480 this.showPreview = function () {
481
482 var _text = self.cm.getValue();
483 var _file_path = $(self.filename_selector).val();
484 if (_text && _file_path) {
485 $('.show-preview').addClass('active');
486 $('.show-editor').removeClass('active');
487
488 $(self.editor_preview_selector).show();
489 $(self.cm.getWrapperElement()).hide();
490
491
492 var post_data = {'text': _text, 'file_path': _file_path, 'csrf_token': CSRF_TOKEN};
493 $(self.editor_preview_selector).html(_gettext('Loading ...'));
494
495 var url = pyroutes.url('file_preview');
496
497 ajaxPOST(url, post_data, function (o) {
498 $(self.editor_preview_selector).html(o);
499 })
500 }
501
502 };
503
504 this.showEditor = function () {
505 $(self.editor_preview_selector).hide();
506 $('.show-editor').addClass('active');
507 $('.show-preview').removeClass('active');
508
509 $(self.cm.getWrapperElement()).show();
510 };
511
512
513 }
514
515 return FileEditor;
516 });
517
@@ -16,58 +16,44 b''
16 16 // # RhodeCode Enterprise Edition, including its added features, Support services,
17 17 // # and proprietary license terms, please see https://rhodecode.com/licenses/
18 18
19 var onSuccessFollow = function(target){
20 var f = $(target);
21 var f_cnt = $('#current_followers_count');
19 var onSuccessFollow = function (target) {
20 var targetEl = $(target);
22 21
23 if(f.hasClass('follow')){
24 f.removeClass('follow');
25 f.addClass('following');
26 f.attr('title', _gettext('Stop following this repository'));
27 $(f).html(_gettext('Unfollow'));
28 if(f_cnt.length){
29 var cnt = Number(f_cnt.html())+1;
30 f_cnt.html(cnt);
22 var callback = function () {
23 targetEl.animate({'opacity': 1.00}, 200);
24 if (targetEl.hasClass('watching')) {
25 targetEl.removeClass('watching');
26 targetEl.attr('title', _gettext('Stopped watching this repository'));
27 $(targetEl).html('<i class="icon-eye"></i>'+_gettext('Watch'));
28 } else {
29 targetEl.addClass('watching');
30 targetEl.attr('title', _gettext('Started watching this repository'));
31 $(targetEl).html('<i class="icon-eye-off"></i>'+_gettext('Unwatch'));
31 32 }
32 }
33 else{
34 f.removeClass('following');
35 f.addClass('follow');
36 f.attr('title', _gettext('Start following this repository'));
37 $(f).html(_gettext('Follow'));
38 if(f_cnt.length){
39 var cnt = Number(f_cnt.html())-1;
40 f_cnt.html(cnt);
41 }
42 }
33 };
34 targetEl.animate({'opacity': 0.15}, 200, callback);
43 35 };
44 36
45 // TODO:: check if the function is needed. 0 usage found
46 var toggleFollowingUser = function(target,follows_user_id,token,user_id){
37
38 var toggleFollowingUser = function (target, follows_user_id) {
47 39 var args = {
48 40 'follows_user_id': follows_user_id,
49 'auth_token': token,
50 41 'csrf_token': CSRF_TOKEN
51 42 };
52 if(user_id != undefined){
53 args.user_id = user_id
54 }
55 ajaxPOST(pyroutes.url('toggle_following'), args, function(){
43
44 ajaxPOST(pyroutes.url('toggle_following'), args, function () {
56 45 onSuccessFollow(target);
57 46 });
58 47 return false;
59 48 };
60 49
61 var toggleFollowingRepo = function(target,follows_repo_id,token,user_id){
50 var toggleFollowingRepo = function (target, follows_repo_id) {
62 51 var args = {
63 52 'follows_repo_id': follows_repo_id,
64 'auth_token': token,
65 53 'csrf_token': CSRF_TOKEN
66 54 };
67 if(user_id != undefined){
68 args.user_id = user_id
69 }
70 ajaxPOST(pyroutes.url('toggle_following'), args, function(){
55
56 ajaxPOST(pyroutes.url('toggle_following'), args, function () {
71 57 onSuccessFollow(target);
72 58 });
73 59 return false;
@@ -73,10 +73,3 b' var select2RefSwitcher = function(target'
73 73 {'repo_name': templateContext.repo_name});
74 74 select2RefBaseSwitcher(targetElement, loadUrl, initialData);
75 75 };
76
77 var select2FileHistorySwitcher = function(targetElement, initialData, state) {
78 var loadUrl = pyroutes.url('repo_file_history',
79 {'repo_name': templateContext.repo_name, 'commit_id': state.rev,
80 'f_path': state.f_path});
81 select2RefBaseSwitcher(targetElement, loadUrl, initialData);
82 };
@@ -9,20 +9,23 b''
9 9 %endif
10 10 </%def>
11 11
12 <%def name="breadcrumbs_links()">
13 ${_('Audit long entry')} ${c.audit_log_entry.entry_id}
14 </%def>
12 <%def name="breadcrumbs_links()"></%def>
15 13
16 14 <%def name="menu_bar_nav()">
17 15 ${self.menu_items(active='admin')}
18 16 </%def>
17
18 <%def name="menu_bar_subnav()">
19 ${self.admin_menu(active='audit_logs')}
20 </%def>
21
19 22 <%def name="main()">
20 23 <div class="box">
21 <!-- box / title -->
24
22 25 <div class="title">
23 ${self.breadcrumbs()}
26 ${_('Audit long entry')} ${c.audit_log_entry.entry_id}
24 27 </div>
25 <!-- end box / title -->
28
26 29 <div class="table">
27 30 <div id="user_log">
28 31 <table class="rctable audit-log">
@@ -8,27 +8,28 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 ${h.form(None, id_="filter_form", method="get")}
13 <input class="q_filter_box ${'' if c.search_term else 'initial'}" id="j_filter" size="15" type="text" name="filter" value="${c.search_term or ''}" placeholder="${_('filter...')}"/>
14 <input type='submit' value="${_('filter')}" class="btn" />
15 ${_('Audit logs')} - ${_ungettext('%s entry', '%s entries', c.audit_logs.item_count) % (c.audit_logs.item_count)}
16 ${h.end_form()}
17 <p class="filterexample" style="position: inherit" onclick="$('#search-help').toggle()">${_('Example Queries')}</p>
18 <pre id="search-help" style="display: none">${h.tooltip(h.journal_filter_help(request))}</pre>
19 </%def>
11 <%def name="breadcrumbs_links()"></%def>
20 12
21 13 <%def name="menu_bar_nav()">
22 14 ${self.menu_items(active='admin')}
23 15 </%def>
24 16
17 <%def name="menu_bar_subnav()">
18 ${self.admin_menu(active='audit_logs')}
19 </%def>
20
25 21 <%def name="main()">
26 22 <div class="box">
27 <!-- box / title -->
28 23 <div class="title">
29 ${self.breadcrumbs()}
24 ${h.form(None, id_="filter_form", method="get")}
25 <input class="q_filter_box ${'' if c.search_term else 'initial'}" id="j_filter" size="15" type="text" name="filter" value="${c.search_term or ''}" placeholder="${_('filter...')}"/>
26 <input type='submit' value="${_('filter')}" class="btn" />
27 ${_('Audit logs')} - ${_ungettext('%s entry', '%s entries', c.audit_logs.item_count) % (c.audit_logs.item_count)}
28 ${h.end_form()}
29 <p class="filterexample" style="position: inherit" onclick="$('#search-help').toggle()">${_('Example Queries')}</p>
30 <pre id="search-help" style="display: none">${h.tooltip(h.journal_filter_help(request))}</pre>
30 31 </div>
31 <!-- end box / title -->
32
32 33 <div class="table">
33 34 <div id="user_log">
34 35 <%include file="/admin/admin_log_base.mako" />
@@ -8,29 +8,26 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 ${h.link_to(_('Admin'),h.route_path('admin_home'))}
13 &raquo;
14 ${_('Authentication Plugins')}
15 </%def>
11 <%def name="breadcrumbs_links()"></%def>
16 12
17 13 <%def name="menu_bar_nav()">
18 14 ${self.menu_items(active='admin')}
19 15 </%def>
20 16
17 <%def name="menu_bar_subnav()">
18 ${self.admin_menu(active='authentication')}
19 </%def>
20
21 21 <%def name="main()">
22 22
23 23 <div class="box">
24 <div class="title">
25 ${self.breadcrumbs()}
26 </div>
27 24
28 25 <div class='sidebar-col-wrapper'>
29 26
30 27 <div class="sidebar">
31 28 <ul class="nav nav-pills nav-stacked">
32 29 % for item in resource.get_root().get_nav_list():
33 <li ${'class=active' if item == resource else ''}>
30 <li ${('class=active' if item == resource else '')}>
34 31 <a href="${request.resource_path(item, route_name='auth_home')}">${item.display_name}</a>
35 32 </li>
36 33 % endfor
@@ -66,10 +63,10 b''
66 63 <th>${_('Plugin ID')}</th>
67 64 <th>${_('Enabled')}</th>
68 65 %for plugin in available_plugins:
69 <tr class="${'inactive' if (not plugin.is_active() and plugin.get_id() in enabled_plugins) else ''}">
66 <tr class="${('inactive' if (not plugin.is_active() and plugin.get_id() in enabled_plugins) else '')}">
70 67 <td>
71 <span plugin_id="${plugin.get_id()}" class="toggle-plugin btn ${'btn-success' if plugin.get_id() in enabled_plugins else ''}">
72 ${_('activated') if plugin.get_id() in enabled_plugins else _('not active')}
68 <span plugin_id="${plugin.get_id()}" class="toggle-plugin btn ${('btn-success' if plugin.get_id() in enabled_plugins else '')}">
69 ${(_('activated') if plugin.get_id() in enabled_plugins else _('not active'))}
73 70 </span>
74 71 </td>
75 72 <td>${plugin.get_display_name()}</td>
@@ -2,10 +2,10 b''
2 2 <%inherit file="/base/base.mako"/>
3 3
4 4 <%def name="title()">
5 ${_('Authentication Settings')}
6 %if c.rhodecode_name:
5 ${_('Authentication Settings')}
6 %if c.rhodecode_name:
7 7 &middot; ${h.branding(c.rhodecode_name)}}
8 %endif
8 %endif
9 9 </%def>
10 10
11 11 <%def name="breadcrumbs_links()">
@@ -17,22 +17,23 b''
17 17 </%def>
18 18
19 19 <%def name="menu_bar_nav()">
20 ${self.menu_items(active='admin')}
20 ${self.menu_items(active='admin')}
21 </%def>
22
23 <%def name="menu_bar_subnav()">
24 ${self.admin_menu(active='authentication')}
21 25 </%def>
22 26
23 27 <%def name="main()">
28
24 29 <div class="box">
25 <div class="title">
26 ${self.breadcrumbs()}
27 </div>
30
28 31 <div class='sidebar-col-wrapper'>
29 32
30 ## TODO: This is repeated in the auth root template and should be merged
31 ## into a single solution.
32 33 <div class="sidebar">
33 34 <ul class="nav nav-pills nav-stacked">
34 35 % for item in resource.get_root().get_nav_list():
35 <li ${'class=active' if item == resource else ''}>
36 <li ${('class=active' if item == resource else '')}>
36 37 <a href="${request.resource_path(item, route_name='auth_home')}">${item.display_name}</a>
37 38 </li>
38 39 % endfor
@@ -18,11 +18,12 b''
18 18 ${self.menu_items(active='admin')}
19 19 </%def>
20 20
21 <%def name="menu_bar_subnav()">
22 ${self.admin_menu(active='defaults')}
23 </%def>
24
21 25 <%def name="main()">
22 26 <div class="box">
23 <div class="title">
24 ${self.breadcrumbs()}
25 </div>
26 27
27 28 ##main
28 29 <div class="sidebar-col-wrapper">
@@ -3,9 +3,9 b''
3 3
4 4 <%def name="title()">
5 5 %if c.show_private:
6 ${_('Private Gists for user %s') % c.rhodecode_user.username}
6 ${_('Private Gists for user {}').format(c.rhodecode_user.username)}
7 7 %elif c.show_public:
8 ${_('Public Gists for user %s') % c.rhodecode_user.username}
8 ${_('Public Gists for user {}').format(c.rhodecode_user.username)}
9 9 %else:
10 10 ${_('Public Gists')}
11 11 %endif
@@ -14,64 +14,59 b''
14 14 %endif
15 15 </%def>
16 16
17 <%def name="breadcrumbs_links()">
18 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
19 %if c.show_private and not c.show_public:
20 ${_('Private Gists for user %s') % c.rhodecode_user.username}
21 %elif c.show_public and not c.show_private:
22 ${_('Public Gists for user %s') % c.rhodecode_user.username}
23 %elif c.show_public and c.show_private:
24 ${_('All Gists for user %s') % c.rhodecode_user.username}
25 %else:
26 ${_('All Public Gists')}
27 %endif
28 - <span id="gists_count">0</span>
29 </%def>
17 <%def name="breadcrumbs_links()"></%def>
30 18
31 19 <%def name="menu_bar_nav()">
32 20 ${self.menu_items(active='gists')}
33 21 </%def>
34 22
23 <%def name="main()">
35 24
25 <div class="box">
26 <div class="title">
36 27
37 <%def name="main()">
38 <div class="box">
39 <div class="title">
40 ${self.breadcrumbs(class_="breadcrumbs block-left")}
28 <ul class="button-links">
29 % if c.is_super_admin:
30 <li class="btn ${('active' if c.active=='all' else '')}"><a href="${h.route_path('gists_show', _query={'all': 1})}">${_('All gists')}</a></li>
31 %endif
32 <li class="btn ${('active' if c.active=='public' else '')}"><a href="${h.route_path('gists_show')}">${_('All public')}</a></li>
41 33 %if c.rhodecode_user.username != h.DEFAULT_USER:
42 <ul class="links block-right">
43 <li>
44 <a href="${h.route_path('gists_new')}" class="btn btn-primary">${_(u'Create New Gist')}</a>
45 </li>
46 </ul>
34 <li class="btn ${('active' if c.active=='my_all' else '')}"><a href="${h.route_path('gists_show', _query={'public':1, 'private': 1})}">${_('My gists')}</a></li>
35 <li class="btn ${('active' if c.active=='my_private' else '')}"><a href="${h.route_path('gists_show', _query={'private': 1})}">${_('My private')}</a></li>
36 <li class="btn ${('active' if c.active=='my_public' else '')}"><a href="${h.route_path('gists_show', _query={'public': 1})}">${_('My public')}</a></li>
47 37 %endif
48 </div>
38 </ul>
49 39
40 % if c.rhodecode_user.username != h.DEFAULT_USER:
41 <div class="pull-right">
42 <a class="btn btn-primary" href="${h.route_path('gists_new')}" >
43 ${_(u'Create New Gist')}
44 </a>
45 </div>
46 % endif
50 47
51 <div class="sidebar-col-wrapper scw-small">
52 ##main
53 <div class="sidebar">
54 <ul class="nav nav-pills nav-stacked">
55 % if h.HasPermissionAll('hg.admin')('access admin gists page'):
56 <li class="${'active' if c.active=='all' else ''}"><a href="${h.route_path('gists_show', _query={'all': 1})}">${_('All gists')}</a></li>
57 %endif
58 <li class="${'active' if c.active=='public' else ''}"><a href="${h.route_path('gists_show')}">${_('All public')}</a></li>
59 %if c.rhodecode_user.username != h.DEFAULT_USER:
60 <li class="${'active' if c.active=='my_all' else ''}"><a href="${h.route_path('gists_show', _query={'public':1, 'private': 1})}">${_('My gists')}</a></li>
61 <li class="${'active' if c.active=='my_private' else ''}"><a href="${h.route_path('gists_show', _query={'private': 1})}">${_('My private')}</a></li>
62 <li class="${'active' if c.active=='my_public' else ''}"><a href="${h.route_path('gists_show', _query={'public': 1})}">${_('My public')}</a></li>
63 %endif
48 <div class="grid-quick-filter">
49 <ul class="grid-filter-box">
50 <li class="grid-filter-box-icon">
51 <i class="icon-search"></i>
52 </li>
53 <li class="grid-filter-box-input">
54 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
55 </li>
64 56 </ul>
65 57 </div>
66 58
67 <div class="main-content">
59 </div>
60
61 <div class="main-content-full-width">
68 62 <div id="repos_list_wrap">
69 63 <table id="gist_list_table" class="display"></table>
70 64 </div>
71 65 </div>
72 </div>
66
73 67 </div>
74 <script>
68
69 <script type="text/javascript">
75 70 $(document).ready(function() {
76 71
77 72 var get_datatable_count = function(){
@@ -48,7 +48,7 b''
48 48 </code>
49 49 </div>
50 50 <div class="stats">
51 %if h.HasPermissionAny('hg.admin')() or c.gist.gist_owner == c.rhodecode_user.user_id:
51 %if c.is_super_admin or c.gist.gist_owner == c.rhodecode_user.user_id:
52 52 <div class="remove_gist">
53 53 ${h.secure_form(h.route_path('gist_delete', gist_id=c.gist.gist_access_id), request=request)}
54 54 ${h.submit('remove_gist', _('Delete'),class_="btn btn-mini btn-danger",onclick="return confirm('"+_('Confirm to delete this Gist')+"');")}
@@ -59,7 +59,7 b''
59 59 ## only owner should see that
60 60 <a href="#copySource" onclick="return false;" class="btn btn-mini icon-clipboard clipboard-action" data-clipboard-text="${c.files[0].content}">${_('Copy content')}</a>
61 61
62 %if h.HasPermissionAny('hg.admin')() or c.gist.gist_owner == c.rhodecode_user.user_id:
62 %if c.is_super_admin or c.gist.gist_owner == c.rhodecode_user.user_id:
63 63 ${h.link_to(_('Edit'), h.route_path('gist_edit', gist_id=c.gist.gist_access_id), class_="btn btn-mini")}
64 64 %endif
65 65 ${h.link_to(_('Show as Raw'), h.route_path('gist_show_formatted', gist_id=c.gist.gist_access_id, revision='tip', format='raw'), class_="btn btn-mini")}
@@ -6,7 +6,7 b''
6 6 elif context['c'].repo_group:
7 7 return "/admin/repo_groups/repo_group_edit.mako"
8 8 else:
9 return "/admin/settings/settings.mako"
9 return "/admin/integrations/global.mako"
10 10 %>
11 11 <%inherit file="${inherit(context)}" />
12 12
@@ -31,12 +31,6 b''
31 31 %endif
32 32 </%def>
33 33
34 <%def name="menu_bar_subnav()">
35 %if c.repo:
36 ${self.repo_menu(active='options')}
37 %endif
38 </%def>
39
40 34 <%def name="main_content()">
41 35 ${next.body()}
42 36 </%def>
@@ -43,7 +43,7 b''
43 43 %if c.repo:
44 44 ${_('Current Integrations for Repository: {repo_name}').format(repo_name=c.repo.repo_name)}
45 45 %elif c.repo_group:
46 ${_('Current Integrations for repository group: {repo_group_name}').format(repo_group_name=c.repo_group.group_name)}
46 ${_('Repository Group Integrations: {}').format(c.repo_group.group_name)}</h3>
47 47 %else:
48 48 ${_('Current Integrations')}
49 49 %endif
@@ -107,11 +107,9 b''
107 107 %for IntegrationType, integration in c.integrations_list:
108 108 <tr id="integration_${integration.integration_id}">
109 109 <td class="td-enabled">
110 %if integration.enabled:
111 <div class="flag_status approved pull-left"></div>
112 %else:
113 <div class="flag_status rejected pull-left"></div>
114 %endif
110 <div class="pull-left">
111 ${h.bool2icon(integration.enabled)}
112 </div>
115 113 </td>
116 114 <td class="td-description">
117 115 ${integration.name}
@@ -23,8 +23,11 b''
23 23 <label class="btn-link btn-danger">${_('Clear')}:</label>
24 24 ${h.checkbox('remove', value=True)}
25 25 </div>
26 </div>
26 </div>
27 27 </div>
28 <p class="help-block help-block-inline" >
29 ${_('Server URL is available as ${server_url} variable. E.g. Redirect url: ${server_url}/_admin/exception_tracker')}
30 </p>
28 31
29 32 <div class="label">
30 33 <label for="redirect_url">${_('Redirect URL')}:</label>
@@ -5,50 +5,59 b''
5 5 <a href="${h.route_path('my_account_edit')}" class="panel-edit">${_('Edit')}</a>
6 6 </div>
7 7
8 <div class="panel-body">
9 <div class="fieldset">
10 <div class="left-label">
8 <div class="panel-body fields">
9 <div class="field">
10 <div class="label">
11 11 ${_('Photo')}:
12 12 </div>
13 <div class="right-content">
14 %if c.visual.use_gravatar:
15 ${base.gravatar(c.user.email, 100)}
16 %else:
17 ${base.gravatar(c.user.email, 20)}
18 ${_('Avatars are disabled')}
19 %endif
13 <div class="input">
14 <div class="text-as-placeholder">
15 %if c.visual.use_gravatar:
16 ${base.gravatar(c.user.email, 100)}
17 %else:
18 ${base.gravatar(c.user.email, 100)}
19 %endif
20 </div>
20 21 </div>
21 22 </div>
22 <div class="fieldset">
23 <div class="left-label">
23 <div class="field">
24 <div class="label">
24 25 ${_('Username')}:
25 26 </div>
26 <div class="right-content">
27 ${c.user.username}
27 <div class="input">
28 <div class="text-as-placeholder">
29 ${c.user.username}
30 </div>
28 31 </div>
29 32 </div>
30 <div class="fieldset">
31 <div class="left-label">
33 <div class="field">
34 <div class="label">
32 35 ${_('First Name')}:
33 36 </div>
34 <div class="right-content">
35 ${c.user.first_name}
37 <div class="input">
38 <div class="text-as-placeholder">
39 ${c.user.first_name}
40 </div>
36 41 </div>
37 42 </div>
38 <div class="fieldset">
39 <div class="left-label">
43 <div class="field">
44 <div class="label">
40 45 ${_('Last Name')}:
41 46 </div>
42 <div class="right-content">
43 ${c.user.last_name}
47 <div class="input">
48 <div class="text-as-placeholder">
49 ${c.user.last_name}
50 </div>
44 51 </div>
45 52 </div>
46 <div class="fieldset">
47 <div class="left-label">
53 <div class="field">
54 <div class="label">
48 55 ${_('Email')}:
49 56 </div>
50 <div class="right-content">
51 ${c.user.email or _('Missing email, please update your user email address.')}
57 <div class="input">
58 <div class="text-as-placeholder">
59 ${c.user.email or _('Missing email, please update your user email address.')}
60 </div>
52 61 </div>
53 62 </div>
54 63 </div>
@@ -58,8 +58,7 b''
58 58 ${base.gravatar(c.user.email, 100)}
59 59 <p class="help-block">${_('Change your avatar at')} <a href="http://gravatar.com">gravatar.com</a>.</p>
60 60 %else:
61 ${base.gravatar(c.user.email, 20)}
62 ${_('Avatars are disabled')}
61 ${base.gravatar(c.user.email, 100)}
63 62 %endif
64 63 </div>
65 64 </div>
@@ -8,9 +8,7 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 ${_('My Notifications')}
13 </%def>
11 <%def name="breadcrumbs_links()"></%def>
14 12
15 13 <%def name="menu_bar_nav()">
16 14 ${self.menu_items(active='my_account')}
@@ -19,7 +17,8 b''
19 17 <%def name="main()">
20 18 <div class="box">
21 19 <div class="title">
22 ${self.breadcrumbs()}
20 ${_('My Notifications')}
21
23 22 <div class="notifications_buttons">
24 23 %if c.notifications:
25 24 <button id='mark_all_read' class="btn btn-default" type="submit">
@@ -18,12 +18,12 b''
18 18 ${self.menu_items(active='admin')}
19 19 </%def>
20 20
21 <%def name="menu_bar_subnav()">
22 ${self.admin_menu(active='permissions')}
23 </%def>
21 24
22 25 <%def name="main()">
23 26 <div class="box">
24 <div class="title">
25 ${self.breadcrumbs()}
26 </div>
27 27
28 28 <div class="sidebar-col-wrapper scw-small">
29 29 ##main
@@ -20,13 +20,12 b''
20 20 ${self.menu_items(active='admin')}
21 21 </%def>
22 22
23 <%def name="menu_bar_subnav()">
24 ${self.admin_menu(active='repository_groups')}
25 </%def>
26
23 27 <%def name="main()">
24 28 <div class="box">
25 <!-- box / title -->
26 <div class="title">
27 ${self.breadcrumbs()}
28 </div>
29 <!-- end box / title -->
30 29 ${h.secure_form(h.route_path('repo_group_create'), request=request)}
31 30 <div class="form">
32 31 <!-- fields -->
@@ -13,7 +13,7 b''
13 13 </%def>
14 14
15 15 <%def name="menu_bar_subnav()">
16 ${self.repo_group_menu(active='options')}
16 ${self.repo_group_menu(active='settings')}
17 17 </%def>
18 18
19 19 <%def name="main_content()">
@@ -23,10 +23,6 b''
23 23 <%def name="main()">
24 24
25 25 <div class="box">
26 <div class="title">
27 ${self.repo_group_page_title(c.repo_group)}
28 </div>
29
30 26 <div class="sidebar-col-wrapper">
31 27 ##main
32 28 <div class="sidebar">
@@ -1,10 +1,16 b''
1 1 <%namespace name="base" file="/base/base.mako"/>
2 2
3 3 <%
4 source_repo_id = c.repo_group.changeset_cache.get('source_repo_id')
5
4 6 elems = [
5 7 (_('Repository Group ID'), c.repo_group.group_id, '', ''),
6 8 (_('Owner'), lambda:base.gravatar_with_user(c.repo_group.user.email), '', ''),
7 9 (_('Created on'), h.format_date(c.repo_group.created_on), '', ''),
10 (_('Updated on'), h.format_date(c.repo_group.updated_on), '', ''),
11 (_('Cached Commit date'), (c.repo_group.changeset_cache.get('date')), '', ''),
12 (_('Cached Commit repo_id'), (h.link_to_if(source_repo_id, source_repo_id, h.route_path('repo_summary', repo_name='_{}'.format(source_repo_id)))), '', ''),
13
8 14 (_('Is Personal Group'), c.repo_group.personal or False, '', ''),
9 15
10 16 (_('Total repositories'), c.repo_group.repositories_recursive_count, '', ''),
@@ -16,7 +22,7 b''
16 22
17 23 <div class="panel panel-default">
18 24 <div class="panel-heading">
19 <h3 class="panel-title">${_('Repository Group: %s') % c.repo_group.group_name}</h3>
25 <h3 class="panel-title">${_('Repository Group Advanced: {}').format(c.repo_group.name)}</h3>
20 26 </div>
21 27 <div class="panel-body">
22 28 ${base.dt_info_panel(elems)}
@@ -2,7 +2,7 b''
2 2
3 3 <div class="panel panel-default">
4 4 <div class="panel-heading">
5 <h3 class="panel-title">${_('Repository Group Permissions')}</h3>
5 <h3 class="panel-title">${_('Repository Group Permissions: {}').format(c.repo_group.name)}</h3>
6 6 </div>
7 7 <div class="panel-body">
8 8 ${h.secure_form(h.route_path('edit_repo_group_perms_update', repo_group_name=c.repo_group.group_name), request=request)}
@@ -141,7 +141,7 b''
141 141 <td class="td-radio">${h.radio('g_perm_%s' % _user_group.users_group_id,'group.admin', checked=_user_group.permission=='group.admin')}</td>
142 142 <td class="td-componentname">
143 143 <i class="icon-user-group"></i>
144 %if h.HasPermissionAny('hg.admin')():
144 %if c.is_super_admin:
145 145 <a href="${h.route_path('edit_user_group',user_group_id=_user_group.users_group_id)}">
146 146 ${_user_group.users_group_name}
147 147 </a>
@@ -3,7 +3,7 b''
3 3
4 4 <div class="panel panel-default">
5 5 <div class="panel-heading">
6 <h3 class="panel-title">${_('Settings for Repository Group: %s') % c.repo_group.name}</h3>
6 <h3 class="panel-title">${_('Repository Group Settings: {}').format(c.repo_group.name)}</h3>
7 7 </div>
8 8 <div class="panel-body">
9 9 ${h.secure_form(h.route_path('edit_repo_group', repo_group_name=c.repo_group.group_name), request=request)}
@@ -8,25 +8,29 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
13 ${h.link_to(_('Admin'),h.route_path('admin_home'))} &raquo; <span id="repo_group_count">0</span> ${_('repository groups')}
14 </%def>
11 <%def name="breadcrumbs_links()"></%def>
15 12
16 13 <%def name="menu_bar_nav()">
17 14 ${self.menu_items(active='admin')}
18 15 </%def>
19 16
17 <%def name="menu_bar_subnav()">
18 ${self.admin_menu(active='repository_groups')}
19 </%def>
20
20 21 <%def name="main()">
21 22 <div class="box">
23
22 24 <div class="title">
23 ${self.breadcrumbs()}
25 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
26 <span id="repo_group_count">0</span> ${_('repository groups')}
27
24 28 <ul class="links">
25 %if h.HasPermissionAny('hg.admin','hg.repogroup.create.true')():
26 <li>
27 <a href="${h.route_path('repo_group_new')}" class="btn btn-small btn-success">${_(u'Add Repository Group')}</a>
28 </li>
29 %endif
29 %if c.can_create_repo_group:
30 <li>
31 <a href="${h.route_path('repo_group_new')}" class="btn btn-small btn-success">${_(u'Add Repository Group')}</a>
32 </li>
33 %endif
30 34 </ul>
31 35 </div>
32 36 <div id="repos_list_wrap">
@@ -36,15 +40,32 b''
36 40
37 41 <script>
38 42 $(document).ready(function() {
39
40 var get_datatable_count = function(){
41 var api = $('#group_list_table').dataTable().api();
42 $('#repo_group_count').text(api.page.info().recordsDisplay);
43 };
43 var $repoGroupsListTable = $('#group_list_table');
44 44
45 45 // repo group list
46 $('#group_list_table').DataTable({
47 data: ${c.data|n},
46 $repoGroupsListTable.DataTable({
47 processing: true,
48 serverSide: true,
49 ajax: {
50 "url": "${h.route_path('repo_groups_data')}",
51 "dataSrc": function (json) {
52 var filteredCount = json.recordsFiltered;
53 var filteredInactiveCount = json.recordsFilteredInactive;
54 var totalInactive = json.recordsTotalInactive;
55 var total = json.recordsTotal;
56
57 var _text = _gettext(
58 "{0} of {1} repository groups").format(
59 filteredCount, total);
60
61 if (total === filteredCount) {
62 _text = _gettext("{0} repository groups").format(total);
63 }
64 $('#repo_group_count').text(_text);
65 return json.data;
66 },
67 },
68
48 69 dom: 'rtp',
49 70 pageLength: ${c.visual.admin_grid_items},
50 71 order: [[ 0, "asc" ]],
@@ -62,36 +83,34 b''
62 83 { data: {"_": "owner",
63 84 "sort": "owner"}, title: "${_('Owner')}", className: "td-user" },
64 85 { data: {"_": "action",
65 "sort": "action"}, title: "${_('Action')}", className: "td-action" }
86 "sort": "action"}, title: "${_('Action')}", className: "td-action", orderable: false }
66 87 ],
67 88 language: {
68 89 paginate: DEFAULT_GRID_PAGINATION,
90 sProcessing: _gettext('loading...'),
69 91 emptyTable: _gettext("No repository groups available yet.")
70 92 },
71 "initComplete": function( settings, json ) {
72 get_datatable_count();
73 quick_repo_menu();
74 }
75 93 });
76 94
77 // update the counter when doing search
78 $('#group_list_table').on( 'search.dt', function (e,settings) {
79 get_datatable_count();
95 $repoGroupsListTable.on('xhr.dt', function(e, settings, json, xhr){
96 $repoGroupsListTable.css('opacity', 1);
97 });
98
99 $repoGroupsListTable.on('preXhr.dt', function(e, settings, data){
100 $repoGroupsListTable.css('opacity', 0.3);
80 101 });
81 102
82 // filter, filter both grids
83 $('#q_filter').on( 'keyup', function () {
103 // filter
104 $('#q_filter').on('keyup',
105 $.debounce(250, function() {
106 $repoGroupsListTable.DataTable().search(
107 $('#q_filter').val()
108 ).draw();
109 })
110 );
111 });
84 112
85 var repo_group_api = $('#group_list_table').dataTable().api();
86 repo_group_api
87 .columns(0)
88 .search(this.value)
89 .draw();
90 });
113 </script>
91 114
92 // refilter table if page load via back button
93 $("#q_filter").trigger('keyup');
94 });
95 </script>
96 115 </%def>
97 116
@@ -26,12 +26,12 b''
26 26 ${self.menu_items(active='admin')}
27 27 </%def>
28 28
29 <%def name="menu_bar_subnav()">
30 ${self.admin_menu(active='repositories')}
31 </%def>
32
29 33 <%def name="main()">
30 34 <div class="box">
31 <!-- box / title -->
32 <div class="title">
33 ${self.breadcrumbs()}
34 </div>
35 35 <%include file="repo_add_base.mako"/>
36 36 </div>
37 37 </%def>
@@ -20,7 +20,7 b''
20 20 </%def>
21 21
22 22 <%def name="menu_bar_subnav()">
23 ${self.repo_menu(active='options')}
23 ${self.repo_menu(active='settings')}
24 24 </%def>
25 25
26 26 <%def name="main_content()">
@@ -34,10 +34,6 b''
34 34
35 35 <%def name="main()">
36 36 <div class="box">
37 <div class="title">
38 ${self.repo_page_title(c.rhodecode_db_repo)}
39
40 </div>
41 37
42 38 <div class="sidebar-col-wrapper scw-small">
43 39 <div class="sidebar">
@@ -7,9 +7,11 b''
7 7 (_('Created on'), h.format_date(c.rhodecode_db_repo.created_on), '', ''),
8 8 (_('Updated on'), h.format_date(c.rhodecode_db_repo.updated_on), '', ''),
9 9 (_('Cached Commit id'), lambda: h.link_to(c.rhodecode_db_repo.changeset_cache.get('short_id'), h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.rhodecode_db_repo.changeset_cache.get('raw_id'))), '', ''),
10 (_('Cached Commit date'), c.rhodecode_db_repo.changeset_cache.get('date'), '', ''),
10 11 (_('Attached scoped tokens'), len(c.rhodecode_db_repo.scoped_tokens), '', [x.user for x in c.rhodecode_db_repo.scoped_tokens]),
11 12 (_('Pull requests source'), len(c.rhodecode_db_repo.pull_requests_source), '', ['pr_id:{}, repo:{}'.format(x.pull_request_id,x.source_repo.repo_name) for x in c.rhodecode_db_repo.pull_requests_source]),
12 13 (_('Pull requests target'), len(c.rhodecode_db_repo.pull_requests_target), '', ['pr_id:{}, repo:{}'.format(x.pull_request_id,x.target_repo.repo_name) for x in c.rhodecode_db_repo.pull_requests_target]),
14 (_('Attached Artifacts'), len(c.rhodecode_db_repo.artifacts), '', ''),
13 15 ]
14 16 %>
15 17
@@ -136,7 +136,7 b''
136 136 <td class="td-radio">${h.radio('g_perm_%s' % _user_group.users_group_id,'repository.admin', checked=_user_group.permission=='repository.admin')}</td>
137 137 <td class="td-componentname">
138 138 <i class="icon-user-group"></i>
139 %if h.HasPermissionAny('hg.admin')():
139 %if c.is_super_admin:
140 140 <a href="${h.route_path('edit_user_group',user_group_id=_user_group.users_group_id)}">
141 141 ${_user_group.users_group_name}
142 142 </a>
@@ -8,25 +8,29 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
13 ${h.link_to(_('Admin'),h.route_path('admin_home'))} &raquo; <span id="repo_count">0</span> ${_('repositories')}
14 </%def>
11 <%def name="breadcrumbs_links()"></%def>
15 12
16 13 <%def name="menu_bar_nav()">
17 14 ${self.menu_items(active='admin')}
18 15 </%def>
19 16
17 <%def name="menu_bar_subnav()">
18 ${self.admin_menu(active='repositories')}
19 </%def>
20
20 21 <%def name="main()">
21 22 <div class="box">
23
22 24 <div class="title">
23 ${self.breadcrumbs()}
25 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
26 <span id="repo_count">0</span> ${_('repositories')}
27
24 28 <ul class="links">
25 %if h.HasPermissionAny('hg.admin','hg.create.repository')():
26 <li>
27 <a href="${h.route_path('repo_new')}" class="btn btn-small btn-success">${_(u'Add Repository')}</a>
28 </li>
29 %endif
29 %if c.can_create_repo:
30 <li>
31 <a href="${h.route_path('repo_new')}" class="btn btn-small btn-success">${_(u'Add Repository')}</a>
32 </li>
33 %endif
30 34 </ul>
31 35 </div>
32 36 <div id="repos_list_wrap">
@@ -66,7 +70,7 b''
66 70 { data: {"_": "state",
67 71 "sort": "state"}, title: "${_('State')}", className: "td-tags td-state" },
68 72 { data: {"_": "action",
69 "sort": "action"}, title: "${_('Action')}", className: "td-action" }
73 "sort": "action"}, title: "${_('Action')}", className: "td-action", orderable: false }
70 74 ],
71 75 language: {
72 76 paginate: DEFAULT_GRID_PAGINATION,
@@ -13,11 +13,15 b''
13 13 &raquo;
14 14 ${_('Settings')}
15 15 </%def>
16
16 ##
17 17 <%def name="menu_bar_nav()">
18 18 ${self.menu_items(active='admin')}
19 19 </%def>
20 20
21 <%def name="menu_bar_subnav()">
22 ${self.admin_menu(active='settings')}
23 </%def>
24
21 25 <%def name="side_bar_nav()">
22 26 % for navitem in c.navlist:
23 27 <li class="${'active' if c.active in navitem.active_list else ''}">
@@ -32,9 +36,6 b''
32 36
33 37 <%def name="main()">
34 38 <div class="box">
35 <div class="title">
36 ${self.breadcrumbs()}
37 </div>
38 39
39 40 ##main
40 41 <div class='sidebar-col-wrapper'>
@@ -6,18 +6,24 b''
6 6 % if c.exception_list_count == 1:
7 7 ${_('There is {} stored exception.').format(c.exception_list_count)}
8 8 % else:
9 ${_('There are {} stored exceptions.').format(c.exception_list_count)}
9 ${_('There are total {} stored exceptions.').format(c.exception_list_count)}
10 10 % endif
11 <br/>
11 12 ${_('Store directory')}: ${c.exception_store_dir}
12 13
13 14 ${h.secure_form(h.route_path('admin_settings_exception_tracker_delete_all'), request=request)}
14 15 <div style="margin: 0 0 20px 0" class="fake-space"></div>
15
16 <input type="hidden" name="type_filter", value="${c.type_filter}">
16 17 <div class="field">
17 18 <button class="btn btn-small btn-danger" type="submit"
18 19 onclick="return confirm('${_('Confirm to delete all exceptions')}');">
19 20 <i class="icon-remove-sign"></i>
20 ${_('Delete All')}
21 % if c.type_filter:
22 ${_('Delete All `{}`').format(c.type_filter)}
23 % else:
24 ${_('Delete All')}
25 % endif
26
21 27 </button>
22 28 </div>
23 29
@@ -48,7 +54,9 b''
48 54 <td><a href="${h.route_path('admin_settings_exception_tracker_show', exception_id=tb['exc_id'])}"><code>${tb['exc_id']}</code></a></td>
49 55 <td>${h.format_date(tb['exc_utc_date'])}</td>
50 56 <td>${tb['app_type']}</td>
51 <td>${tb['exc_type']}</td>
57 <td>
58 <a href="${h.current_route_path(request, type_filter=tb['exc_type'])}">${tb['exc_type']}</a>
59 </td>
52 60 </tr>
53 61 <% cnt -=1 %>
54 62 % endfor
@@ -19,13 +19,12 b''
19 19 ${self.menu_items(active='admin')}
20 20 </%def>
21 21
22 <%def name="menu_bar_subnav()">
23 ${self.admin_menu(active='user_groups')}
24 </%def>
25
22 26 <%def name="main()">
23 27 <div class="box main-content">
24 <!-- box / title -->
25 <div class="title">
26 ${self.breadcrumbs()}
27 </div>
28 <!-- end box / title -->
29 28 ${h.secure_form(h.route_path('user_groups_create'), request=request)}
30 29 <div class="form">
31 30 <!-- fields -->
@@ -20,11 +20,12 b''
20 20 ${self.menu_items(active='admin')}
21 21 </%def>
22 22
23 <%def name="menu_bar_subnav()">
24 ${self.admin_menu(active='user_groups')}
25 </%def>
26
23 27 <%def name="main()">
24 28 <div class="box">
25 <div class="title">
26 ${self.breadcrumbs()}
27 </div>
28 29
29 30 ##main
30 31 <div class="sidebar-col-wrapper">
@@ -143,7 +143,7 b''
143 143 <td class="td-radio">${h.radio('g_perm_%s' % _user_group.users_group_id,'usergroup.admin')}</td>
144 144 <td class="td-user">
145 145 <i class="icon-user-group"></i>
146 %if h.HasPermissionAny('hg.admin')():
146 %if c.is_super_admin:
147 147 <a href="${h.route_path('edit_user_group',user_group_id=_user_group.users_group_id)}">
148 148 ${_user_group.users_group_name}
149 149 </a>
@@ -8,25 +8,28 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
13 ${h.link_to(_('Admin'),h.route_path('admin_home'))} &raquo; <span id="user_group_count">0</span>
14 </%def>
11 <%def name="breadcrumbs_links()"></%def>
15 12
16 13 <%def name="menu_bar_nav()">
17 14 ${self.menu_items(active='admin')}
18 15 </%def>
19 16
17 <%def name="menu_bar_subnav()">
18 ${self.admin_menu(active='user_groups')}
19 </%def>
20
20 21 <%def name="main()">
21 22 <div class="box">
22 23
23 24 <div class="title">
24 ${self.breadcrumbs()}
25 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
26 <span id="user_group_count">0</span>
27
25 28 <ul class="links">
26 %if h.HasPermissionAny('hg.admin', 'hg.usergroup.create.true')():
27 <li>
28 <a href="${h.route_path('user_groups_new')}" class="btn btn-small btn-success">${_(u'Add User Group')}</a>
29 </li>
29 %if c.can_create_user_group:
30 <li>
31 <a href="${h.route_path('user_groups_new')}" class="btn btn-small btn-success">${_(u'Add User Group')}</a>
32 </li>
30 33 %endif
31 34 </ul>
32 35 </div>
@@ -102,7 +105,7 b''
102 105 // filter
103 106 $('#q_filter').on('keyup',
104 107 $.debounce(250, function() {
105 $('#user_group_list_table').DataTable().search(
108 $userGroupsListTable.DataTable().search(
106 109 $('#q_filter').val()
107 110 ).draw();
108 111 })
@@ -13,25 +13,26 b''
13 13 &raquo;
14 14 ${h.link_to(_('Users'),h.route_path('users'))}
15 15 &raquo;
16 % if c.user.active:
17 ${c.user.username}
18 % else:
19 <strike title="${_('This user is set as disabled')}">${c.user.username}</strike>
20 % endif
21
22 16 </%def>
23 17
24 18 <%def name="menu_bar_nav()">
25 19 ${self.menu_items(active='admin')}
26 20 </%def>
27 21
22 <%def name="menu_bar_subnav()">
23 ${self.admin_menu(active='users')}
24 </%def>
25
26
28 27 <%def name="main()">
29 28 <div class="box user_settings">
30 <div class="title">
31 ${self.breadcrumbs()}
29 % if not c.user.active:
30 <div class="alert alert-warning text-center">
31 <strong>${_('This user is set as disabled')}</strong>
32 32 </div>
33 % endif
33 34
34 ##main
35 ##main
35 36 <div class="sidebar-col-wrapper">
36 37 <div class="sidebar">
37 38 <ul class="nav nav-pills nav-stacked">
@@ -81,7 +81,7 b''
81 81 </div>
82 82 %endif
83 83 <button class="btn btn-default" type="submit" ${'disabled="disabled"' if c.personal_repo_group else ''}>
84 <i class="icon-folder-close"></i>
84 <i class="icon-repo-group"></i>
85 85 ${_('Create personal repository group')}
86 86 </button>
87 87 ${h.end_form()}
@@ -61,9 +61,9 b''
61 61 </div>
62 62 <div class="input">
63 63 ${h.text('new_ip')} ${h.text('description', placeholder=_('Description...'))}
64 <span class="help-block">${_('Enter comma separated list of ip addresses like 127.0.0.1,\n'
65 'or use a ip address with a mask 127.0.0.1/24, to create a network range.\n'
66 'To specify multiple address range use 127.0.0.1-127.0.0.10 syntax')}</span>
64 <span class="help-block pre-formatting">${_('Enter comma separated list of ip addresses like 10.0.0.1,10.0.0.2.\n'
65 'Use a ip address with a mask 127.0.0.1/24, to create a network match pattern.\n'
66 'To specify multiple entries on an address range use 127.0.0.1-127.0.0.10 syntax')}</span>
67 67 </div>
68 68 </div>
69 69 <div class="buttons">
@@ -29,8 +29,7 b''
29 29 ${base.gravatar(c.user.email, 100)}
30 30 <p class="help-block">${_('Change the avatar at')} <a href="http://gravatar.com">gravatar.com</a>.</p>
31 31 %else:
32 ${base.gravatar(c.user.email, 20)}
33 ${_('Avatars are disabled')}
32 ${base.gravatar(c.user.email, 100)}
34 33 %endif
35 34 </div>
36 35 </div>
@@ -8,21 +8,24 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
13 ${h.link_to(_('Admin'),h.route_path('admin_home'))} &raquo; <span id="user_count">0</span>
14 </%def>
11 <%def name="breadcrumbs_links()"></%def>
15 12
16 13 <%def name="menu_bar_nav()">
17 14 ${self.menu_items(active='admin')}
18 15 </%def>
19 16
17 <%def name="menu_bar_subnav()">
18 ${self.admin_menu(active='users')}
19 </%def>
20
20 21 <%def name="main()">
21 22
22 23 <div class="box">
23 24
24 25 <div class="title">
25 ${self.breadcrumbs()}
26 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
27 <span id="user_count">0</span>
28
26 29 <ul class="links">
27 30 <li>
28 31 <a href="${h.route_path('users_new')}" class="btn btn-small btn-success">${_(u'Add User')}</a>
@@ -9,11 +9,13 b''
9 9 <div id="header-inner" class="wrapper">
10 10 <div id="logo">
11 11 <div class="logo-wrapper">
12 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-216x60.png')}" alt="RhodeCode"/></a>
12 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-60x60.png')}" alt="RhodeCode"/></a>
13 13 </div>
14 %if c.rhodecode_name:
15 <div class="branding">- ${h.branding(c.rhodecode_name)}</div>
16 %endif
14 % if c.rhodecode_name:
15 <div class="branding">
16 <a href="${h.route_path('home')}">${h.branding(c.rhodecode_name)}</a>
17 </div>
18 % endif
17 19 </div>
18 20 <!-- MENU BAR NAV -->
19 21 ${self.menu_bar_nav()}
@@ -72,22 +74,67 b''
72 74 </div>
73 75 </%def>
74 76
75 <%def name="admin_menu()">
76 <ul class="admin_menu submenu">
77 <li><a href="${h.route_path('admin_audit_logs')}">${_('Admin audit logs')}</a></li>
78 <li><a href="${h.route_path('repos')}">${_('Repositories')}</a></li>
79 <li><a href="${h.route_path('repo_groups')}">${_('Repository groups')}</a></li>
80 <li><a href="${h.route_path('users')}">${_('Users')}</a></li>
81 <li><a href="${h.route_path('user_groups')}">${_('User groups')}</a></li>
82 <li><a href="${h.route_path('admin_permissions_application')}">${_('Permissions')}</a></li>
83 <li><a href="${h.route_path('auth_home', traverse='')}">${_('Authentication')}</a></li>
84 <li><a href="${h.route_path('global_integrations_home')}">${_('Integrations')}</a></li>
85 <li><a href="${h.route_path('admin_defaults_repositories')}">${_('Defaults')}</a></li>
86 <li class="last"><a href="${h.route_path('admin_settings')}">${_('Settings')}</a></li>
87 </ul>
77 <%def name="admin_menu(active=None)">
78 <%
79 def is_active(selected):
80 if selected == active:
81 return "active"
82 %>
83
84 <div id="context-bar">
85 <div class="wrapper">
86 <div class="title">
87 <div class="title-content">
88 <div class="title-main">
89 % if c.is_super_admin:
90 ${_('Super Admin Panel')}
91 % else:
92 ${_('Delegated Admin Panel')}
93 % endif
94 </div>
95 </div>
96 </div>
97
98 <ul id="context-pages" class="navigation horizontal-list">
99
100 ## super admin case
101 % if c.is_super_admin:
102 <li class="${is_active('audit_logs')}"><a href="${h.route_path('admin_audit_logs')}">${_('Admin audit logs')}</a></li>
103 <li class="${is_active('repositories')}"><a href="${h.route_path('repos')}">${_('Repositories')}</a></li>
104 <li class="${is_active('repository_groups')}"><a href="${h.route_path('repo_groups')}">${_('Repository groups')}</a></li>
105 <li class="${is_active('users')}"><a href="${h.route_path('users')}">${_('Users')}</a></li>
106 <li class="${is_active('user_groups')}"><a href="${h.route_path('user_groups')}">${_('User groups')}</a></li>
107 <li class="${is_active('permissions')}"><a href="${h.route_path('admin_permissions_application')}">${_('Permissions')}</a></li>
108 <li class="${is_active('authentication')}"><a href="${h.route_path('auth_home', traverse='')}">${_('Authentication')}</a></li>
109 <li class="${is_active('integrations')}"><a href="${h.route_path('global_integrations_home')}">${_('Integrations')}</a></li>
110 <li class="${is_active('defaults')}"><a href="${h.route_path('admin_defaults_repositories')}">${_('Defaults')}</a></li>
111 <li class="${is_active('settings')}"><a href="${h.route_path('admin_settings')}">${_('Settings')}</a></li>
112
113 ## delegated admin
114 % elif c.is_delegated_admin:
115 <%
116 repositories=c.auth_user.repositories_admin or c.can_create_repo
117 repository_groups=c.auth_user.repository_groups_admin or c.can_create_repo_group
118 user_groups=c.auth_user.user_groups_admin or c.can_create_user_group
119 %>
120
121 %if repositories:
122 <li class="${is_active('repositories')} local-admin-repos"><a href="${h.route_path('repos')}">${_('Repositories')}</a></li>
123 %endif
124 %if repository_groups:
125 <li class="${is_active('repository_groups')} local-admin-repo-groups"><a href="${h.route_path('repo_groups')}">${_('Repository groups')}</a></li>
126 %endif
127 %if user_groups:
128 <li class="${is_active('user_groups')} local-admin-user-groups"><a href="${h.route_path('user_groups')}">${_('User groups')}</a></li>
129 %endif
130 % endif
131 </ul>
132
133 </div>
134 <div class="clear"></div>
135 </div>
88 136 </%def>
89 137
90
91 138 <%def name="dt_info_panel(elements)">
92 139 <dl class="dl-horizontal">
93 140 %for dt, dd, title, show_items in elements:
@@ -117,7 +164,6 b''
117 164 </dl>
118 165 </%def>
119 166
120
121 167 <%def name="gravatar(email, size=16)">
122 168 <%
123 169 if (size > 16):
@@ -143,23 +189,9 b''
143 189 </%def>
144 190
145 191
146 ## admin menu used for people that have some admin resources
147 <%def name="admin_menu_simple(repositories=None, repository_groups=None, user_groups=None)">
148 <ul class="submenu">
149 %if repositories:
150 <li class="local-admin-repos"><a href="${h.route_path('repos')}">${_('Repositories')}</a></li>
151 %endif
152 %if repository_groups:
153 <li class="local-admin-repo-groups"><a href="${h.route_path('repo_groups')}">${_('Repository groups')}</a></li>
154 %endif
155 %if user_groups:
156 <li class="local-admin-user-groups"><a href="${h.route_path('user_groups')}">${_('User groups')}</a></li>
157 %endif
158 </ul>
159 </%def>
192 <%def name="repo_page_title(repo_instance)">
193 <div class="title-content repo-title">
160 194
161 <%def name="repo_page_title(repo_instance)">
162 <div class="title-content">
163 195 <div class="title-main">
164 196 ## SVN/HG/GIT icons
165 197 %if h.is_hg(repo_instance):
@@ -182,11 +214,29 b''
182 214 ## repo name with group name
183 215 ${h.breadcrumb_repo_link(repo_instance)}
184 216
217 ## Context Actions
218 <div class="pull-right">
219 %if c.rhodecode_user.username != h.DEFAULT_USER:
220 <a href="${h.route_path('atom_feed_home', repo_name=c.rhodecode_db_repo.repo_name, _query=dict(auth_token=c.rhodecode_user.feed_token))}" title="${_('RSS Feed')}" class="btn btn-sm"><i class="icon-rss-sign"></i>RSS</a>
221
222 <a href="#WatchRepo" onclick="toggleFollowingRepo(this, templateContext.repo_id); return false" title="${_('Watch this Repository and actions on it in your personalized journal')}" class="btn btn-sm ${('watching' if c.repository_is_user_following else '')}">
223 % if c.repository_is_user_following:
224 <i class="icon-eye-off"></i>${_('Unwatch')}
225 % else:
226 <i class="icon-eye"></i>${_('Watch')}
227 % endif
228
229 </a>
230 %else:
231 <a href="${h.route_path('atom_feed_home', repo_name=c.rhodecode_db_repo.repo_name)}" title="${_('RSS Feed')}" class="btn btn-sm"><i class="icon-rss-sign"></i>RSS</a>
232 %endif
233 </div>
234
185 235 </div>
186 236
187 237 ## FORKED
188 238 %if repo_instance.fork:
189 <p>
239 <p class="discreet">
190 240 <i class="icon-code-fork"></i> ${_('Fork of')}
191 241 ${h.link_to_if(c.has_origin_repo_read_perm,repo_instance.fork.repo_name, h.route_path('repo_summary', repo_name=repo_instance.fork.repo_name))}
192 242 </p>
@@ -194,7 +244,7 b''
194 244
195 245 ## IMPORTED FROM REMOTE
196 246 %if repo_instance.clone_uri:
197 <p>
247 <p class="discreet">
198 248 <i class="icon-code-fork"></i> ${_('Clone from')}
199 249 <a href="${h.safe_str(h.hide_credentials(repo_instance.clone_uri))}">${h.hide_credentials(repo_instance.clone_uri)}</a>
200 250 </p>
@@ -202,12 +252,12 b''
202 252
203 253 ## LOCKING STATUS
204 254 %if repo_instance.locked[0]:
205 <p class="locking_locked">
255 <p class="locking_locked discreet">
206 256 <i class="icon-repo-lock"></i>
207 257 ${_('Repository locked by %(user)s') % {'user': h.person_by_id(repo_instance.locked[0])}}
208 258 </p>
209 259 %elif repo_instance.enable_locking:
210 <p class="locking_unlocked">
260 <p class="locking_unlocked discreet">
211 261 <i class="icon-repo-unlock"></i>
212 262 ${_('Repository not locked. Pull repository to lock it.')}
213 263 </p>
@@ -222,78 +272,81 b''
222 272 if selected == active:
223 273 return "active"
224 274 %>
275 % if c.rhodecode_db_repo.archived:
276 <div class="alert alert-warning text-center">
277 <strong>${_('This repository has been archived. It is now read-only.')}</strong>
278 </div>
279 % endif
225 280
226 <!--- CONTEXT BAR -->
281 <!--- REPO CONTEXT BAR -->
227 282 <div id="context-bar">
228 283 <div class="wrapper">
284
285 <div class="title">
286 ${self.repo_page_title(c.rhodecode_db_repo)}
287 </div>
288
229 289 <ul id="context-pages" class="navigation horizontal-list">
230 290 <li class="${is_active('summary')}"><a class="menulink" href="${h.route_path('repo_summary', repo_name=c.repo_name)}"><div class="menulabel">${_('Summary')}</div></a></li>
231 <li class="${is_active('changelog')}"><a class="menulink" href="${h.route_path('repo_changelog', repo_name=c.repo_name)}"><div class="menulabel">${_('Changelog')}</div></a></li>
291 <li class="${is_active('commits')}"><a class="menulink" href="${h.route_path('repo_commits', repo_name=c.repo_name)}"><div class="menulabel">${_('Commits')}</div></a></li>
232 292 <li class="${is_active('files')}"><a class="menulink" href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.rhodecode_db_repo.landing_rev[1], f_path='')}"><div class="menulabel">${_('Files')}</div></a></li>
233 293 <li class="${is_active('compare')}"><a class="menulink" href="${h.route_path('repo_compare_select',repo_name=c.repo_name)}"><div class="menulabel">${_('Compare')}</div></a></li>
234 <li class="${is_active('search')}"><a class="menulink" href="${h.route_path('search_repo',repo_name=c.repo_name)}"><div class="menulabel">${_('Search')}</div></a></li>
235 294
236 295 ## TODO: anderson: ideally it would have a function on the scm_instance "enable_pullrequest() and enable_fork()"
237 296 %if c.rhodecode_db_repo.repo_type in ['git','hg']:
238 297 <li class="${is_active('showpullrequest')}">
239 298 <a class="menulink" href="${h.route_path('pullrequest_show_all', repo_name=c.repo_name)}" title="${h.tooltip(_('Show Pull Requests for %s') % c.repo_name)}">
240 %if c.repository_pull_requests:
241 <span class="pr_notifications">${c.repository_pull_requests}</span>
299 <div class="menulabel">
300 %if c.repository_pull_requests == 1:
301 ${_('Pull Request')} ${c.repository_pull_requests}
302 %else:
303 ${_('Pull Requests')} ${c.repository_pull_requests}
242 304 %endif
243 <div class="menulabel">${_('Pull Requests')}</div>
305 </div>
244 306 </a>
245 307 </li>
246 308 %endif
247 309
310 <li class="${is_active('artifacts')}"><a class="menulink" href="${h.route_path('repo_artifacts_list',repo_name=c.repo_name)}"><div class="menulabel">${_('Artifacts')} (BETA)</div></a></li>
311
312 %if h.HasRepoPermissionAll('repository.admin')(c.repo_name):
313 <li class="${is_active('settings')}"><a class="menulink" href="${h.route_path('edit_repo',repo_name=c.repo_name)}"><div class="menulabel">${_('Repository Settings')}</div></a></li>
314 %endif
315
316 ## determine if we have "any" option available
317 <%
318 can_lock = h.HasRepoPermissionAny('repository.write','repository.admin')(c.repo_name) and c.rhodecode_db_repo.enable_locking
319 has_actions = (c.rhodecode_user.username != h.DEFAULT_USER and c.rhodecode_db_repo.repo_type in ['git','hg'] ) or can_lock
320 %>
248 321 <li class="${is_active('options')}">
249 <a class="menulink dropdown">
250 <div class="menulabel">${_('Options')} <div class="show_more"></div></div>
251 </a>
252 <ul class="submenu">
253 %if h.HasRepoPermissionAll('repository.admin')(c.repo_name):
254 <li><a href="${h.route_path('edit_repo',repo_name=c.repo_name)}">${_('Repository Settings')}</a></li>
255 %endif
256 %if c.rhodecode_db_repo.fork:
257 <li>
258 <a title="${h.tooltip(_('Compare fork with %s' % c.rhodecode_db_repo.fork.repo_name))}"
259 href="${h.route_path('repo_compare',
260 repo_name=c.rhodecode_db_repo.fork.repo_name,
261 source_ref_type=c.rhodecode_db_repo.landing_rev[0],
262 source_ref=c.rhodecode_db_repo.landing_rev[1],
263 target_repo=c.repo_name,target_ref_type='branch' if request.GET.get('branch') else c.rhodecode_db_repo.landing_rev[0],
264 target_ref=request.GET.get('branch') or c.rhodecode_db_repo.landing_rev[1],
265 _query=dict(merge=1))}"
266 >
267 ${_('Compare fork')}
268 </a>
269 </li>
270 %endif
322 % if has_actions:
323 <a class="menulink dropdown">
324 <div class="menulabel">${_('Options')}<div class="show_more"></div></div>
325 </a>
326 <ul class="submenu">
327 <li><a href="${h.route_path('repo_fork_new',repo_name=c.repo_name)}">${_('Fork this repository')}</a></li>
328 <li><a href="${h.route_path('pullrequest_new',repo_name=c.repo_name)}">${_('Create Pull Request')}</a></li>
329 %if can_lock:
330 %if c.rhodecode_db_repo.locked[0]:
331 <li><a class="locking_del" href="${h.route_path('repo_edit_toggle_locking',repo_name=c.repo_name)}">${_('Unlock Repository')}</a></li>
332 %else:
333 <li><a class="locking_add" href="${h.route_path('repo_edit_toggle_locking',repo_name=c.repo_name)}">${_('Lock Repository')}</a></li>
334 %endif
335 %endif
336 </ul>
337 % else:
338 <a class="menulink disabled">
339 <div class="menulabel">${_('Options')}<div class="show_more"></div></div>
340 </a>
341 % endif
342 </li>
271 343
272 %if h.HasRepoPermissionAny('repository.write','repository.admin')(c.repo_name) and c.rhodecode_db_repo.enable_locking:
273 %if c.rhodecode_db_repo.locked[0]:
274 <li><a class="locking_del" href="${h.route_path('repo_edit_toggle_locking',repo_name=c.repo_name)}">${_('Unlock')}</a></li>
275 %else:
276 <li><a class="locking_add" href="${h.route_path('repo_edit_toggle_locking',repo_name=c.repo_name)}">${_('Lock')}</a></li>
277 %endif
278 %endif
279 %if c.rhodecode_user.username != h.DEFAULT_USER:
280 %if c.rhodecode_db_repo.repo_type in ['git','hg']:
281 <li><a href="${h.route_path('repo_fork_new',repo_name=c.repo_name)}">${_('Fork')}</a></li>
282 <li><a href="${h.route_path('pullrequest_new',repo_name=c.repo_name)}">${_('Create Pull Request')}</a></li>
283 %endif
284 %endif
285 </ul>
286 </li>
287 344 </ul>
288 345 </div>
289 346 <div class="clear"></div>
290 347 </div>
291 % if c.rhodecode_db_repo.archived:
292 <div class="alert alert-warning text-center">
293 <strong>${_('This repository has been archived. It is now read-only.')}</strong>
294 </div>
295 % endif
296 <!--- END CONTEXT BAR -->
348
349 <!--- REPO END CONTEXT BAR -->
297 350
298 351 </%def>
299 352
@@ -301,14 +354,14 b''
301 354 <div class="title-content">
302 355 <div class="title-main">
303 356 ## Repository Group icon
304 <i class="icon-folder-close"></i>
357 <i class="icon-repo-group"></i>
305 358
306 359 ## repo name with group name
307 360 ${h.breadcrumb_repo_group_link(repo_group_instance)}
308 361 </div>
309 362
310 363 <%namespace name="dt" file="/data_table/_dt_elements.mako"/>
311 <div class="repo-group-desc">
364 <div class="repo-group-desc discreet">
312 365 ${dt.repo_group_desc(repo_group_instance.description_safe, repo_group_instance.personal, c.visual.stylify_metatags)}
313 366 </div>
314 367
@@ -321,8 +374,6 b''
321 374 if selected == active:
322 375 return "active"
323 376
324 is_admin = h.HasPermissionAny('hg.admin')('can create repos index page')
325
326 377 gr_name = c.repo_group.group_name if c.repo_group else None
327 378 # create repositories with write permission on group is set to true
328 379 create_on_write = h.HasPermissionAny('hg.create.write_on_repogroup.true')()
@@ -331,35 +382,49 b''
331 382
332 383 %>
333 384
334 <!--- CONTEXT BAR -->
385 <!--- REPO GROUP CONTEXT BAR -->
335 386 <div id="context-bar">
336 387 <div class="wrapper">
388 <div class="title">
389 ${self.repo_group_page_title(c.repo_group)}
390 </div>
391
337 392 <ul id="context-pages" class="navigation horizontal-list">
338 393 <li class="${is_active('home')}"><a class="menulink" href="${h.route_path('repo_group_home', repo_group_name=c.repo_group.group_name)}"><div class="menulabel">${_('Group Home')}</div></a></li>
339 <li class="${is_active('search')}"><a class="menulink" href="${h.route_path('search_repo_group', repo_group_name=c.repo_group.group_name)}"><div class="menulabel">${_('Search')}</div></a></li>
340
394 % if c.is_super_admin or group_admin:
395 <li class="${is_active('settings')}"><a class="menulink" href="${h.route_path('edit_repo_group',repo_group_name=c.repo_group.group_name)}" title="${_('You have admin right to this group, and can edit it')}"><div class="menulabel">${_('Group Settings')}</div></a></li>
396 % endif
397 ## determine if we have "any" option available
398 <%
399 can_create_repos = c.is_super_admin or group_admin or (group_write and create_on_write)
400 can_create_repo_groups = c.is_super_admin or group_admin
401 has_actions = can_create_repos or can_create_repo_groups
402 %>
341 403 <li class="${is_active('options')}">
342 <a class="menulink dropdown">
404 % if has_actions:
405 <a class="menulink dropdown">
343 406 <div class="menulabel">${_('Options')} <div class="show_more"></div></div>
344 </a>
345 <ul class="submenu">
346 %if is_admin or group_admin:
347 <li><a href="${h.route_path('edit_repo_group',repo_group_name=c.repo_group.group_name)}" title="${_('You have admin right to this group, and can edit it')}">${_('Group Settings')}</a></li>
348 %endif
349 %if is_admin or group_admin or (group_write and create_on_write):
407 </a>
408 <ul class="submenu">
409 %if can_create_repos:
350 410 <li><a href="${h.route_path('repo_new',_query=dict(parent_group=c.repo_group.group_id))}">${_('Add Repository')}</a></li>
351 411 %endif
352 %if is_admin or group_admin:
353 <li><a href="${h.route_path('repo_group_new',_query=dict(parent_group=c.repo_group.group_id))}">${_(u'Add Parent Group')}</a></li>
412 %if can_create_repo_groups:
413 <li><a href="${h.route_path('repo_group_new',_query=dict(parent_group=c.repo_group.group_id))}">${_(u'Add Repository Group')}</a></li>
354 414 %endif
355 </ul>
415 </ul>
416 % else:
417 <a class="menulink disabled">
418 <div class="menulabel">${_('Options')} <div class="show_more"></div></div>
419 </a>
420 % endif
356 421 </li>
357 422 </ul>
358 423 </div>
359 424 <div class="clear"></div>
360 425 </div>
361 426
362 <!--- END CONTEXT BAR -->
427 <!--- REPO GROUP CONTEXT BAR -->
363 428
364 429 </%def>
365 430
@@ -431,7 +496,7 b''
431 496 <div>
432 497 <a class="bookmark-item" href="${h.route_path('my_account_goto_bookmark', bookmark_id=item.position)}">
433 498 <code>${item.position}</code>
434 <i class="icon-folder-close" title="${_('Repository group')}" style="font-size: 16px"></i>
499 <i class="icon-repo-group" title="${_('Repository group')}" style="font-size: 14px"></i>
435 500 ${(item.title or h.shorter(item.repository_group.group_name, 30))}
436 501 </a>
437 502 </div>
@@ -484,10 +549,35 b''
484 549 <li>
485 550 <div class="menulabel main_filter_box">
486 551 <div class="main_filter_input_box">
487 <input class="main_filter_input" id="main_filter" size="15" type="text" name="main_filter" placeholder="${_('search / go to...')}" value=""/>
488 </div>
489 <div class="main_filter_help_box">
490 <a href="#showFilterHelp" onclick="showMainFilterBox(); return false">?</a>
552 <ul class="searchItems">
553
554 % if c.template_context['search_context']['repo_id']:
555 <li class="searchTag searchTagFilter searchTagHidable" >
556 ##<a href="${h.route_path('search_repo',repo_name=c.template_context['search_context']['repo_name'])}">
557 <span class="tag">
558 This repo
559 <a href="#removeGoToFilter" onclick="removeGoToFilter(); return false"><i class="icon-cancel-circled"></i></a>
560 </span>
561 ##</a>
562 </li>
563 % elif c.template_context['search_context']['repo_group_id']:
564 <li class="searchTag searchTagFilter searchTagHidable">
565 ##<a href="${h.route_path('search_repo_group',repo_group_name=c.template_context['search_context']['repo_group_name'])}">
566 <span class="tag">
567 This group
568 <a href="#removeGoToFilter" onclick="removeGoToFilter(); return false"><i class="icon-cancel-circled"></i></a>
569 </span>
570 ##</a>
571 </li>
572 % endif
573
574 <li class="searchTagInput">
575 <input class="main_filter_input" id="main_filter" size="25" type="text" name="main_filter" placeholder="${_('search / go to...')}" value="" />
576 </li>
577 <li class="searchTag searchTagHelp">
578 <a href="#showFilterHelp" onclick="showMainFilterBox(); return false">?</a>
579 </li>
580 </ul>
491 581 </div>
492 582 </div>
493 583
@@ -498,15 +588,31 b''
498 588
499 589 - Prefix query to allow special search:
500 590
501 user:admin, to search for usernames
591 user:admin, to search for usernames, always global
592
593 user_group:devops, to search for user groups, always global
594
595 commit:efced4, to search for commits, scoped to repositories or groups
596
597 file:models.py, to search for file paths, scoped to repositories or groups
502 598
503 user_group:devops, to search for user groups
504
505 commit:efced4, to search for commits
599 % if c.template_context['search_context']['repo_id']:
600 For advanced full text search visit: <a href="${h.route_path('search_repo',repo_name=c.template_context['search_context']['repo_name'])}">repository search</a>
601 % elif c.template_context['search_context']['repo_group_id']:
602 For advanced full text search visit: <a href="${h.route_path('search_repo_group',repo_group_name=c.template_context['search_context']['repo_group_name'])}">repository group search</a>
603 % else:
604 For advanced full text search visit: <a href="${h.route_path('search')}">global search</a>
605 % endif
506 606 </div>
507 607 </li>
508 608
509 609 ## ROOT MENU
610 <li class="${is_active('home')}">
611 <a class="menulink" title="${_('Home')}" href="${h.route_path('home')}">
612 <div class="menulabel">${_('Home')}</div>
613 </a>
614 </li>
615
510 616 %if c.rhodecode_user.username != h.DEFAULT_USER:
511 617 <li class="${is_active('journal')}">
512 618 <a class="menulink" title="${_('Show activity journal')}" href="${h.route_path('journal')}">
@@ -520,33 +626,21 b''
520 626 </a>
521 627 </li>
522 628 %endif
629
523 630 <li class="${is_active('gists')}">
524 631 <a class="menulink childs" title="${_('Show Gists')}" href="${h.route_path('gists_show')}">
525 632 <div class="menulabel">${_('Gists')}</div>
526 633 </a>
527 634 </li>
528 <li class="${is_active('search')}">
529 <a class="menulink" title="${_('Search in repositories you have access to')}" href="${h.route_path('search')}">
530 <div class="menulabel">${_('Search')}</div>
531 </a>
532 </li>
533 % if h.HasPermissionAll('hg.admin')('access admin main page'):
635
636 % if c.is_super_admin or c.is_delegated_admin:
534 637 <li class="${is_active('admin')}">
535 <a class="menulink childs" title="${_('Admin settings')}" href="#" onclick="return false;">
536 <div class="menulabel">${_('Admin')} <div class="show_more"></div></div>
638 <a class="menulink childs" title="${_('Admin settings')}" href="${h.route_path('admin_home')}">
639 <div class="menulabel">${_('Admin')} </div>
537 640 </a>
538 ${admin_menu()}
539 641 </li>
540 % elif c.rhodecode_user.repositories_admin or c.rhodecode_user.repository_groups_admin or c.rhodecode_user.user_groups_admin:
541 <li class="${is_active('admin')}">
542 <a class="menulink childs" title="${_('Delegated Admin settings')}">
543 <div class="menulabel">${_('Admin')} <div class="show_more"></div></div>
544 </a>
545 ${admin_menu_simple(c.rhodecode_user.repositories_admin,
546 c.rhodecode_user.repository_groups_admin,
547 c.rhodecode_user.user_groups_admin or h.HasPermissionAny('hg.usergroup.create.true')())}
548 </li>
549 % endif
642 % endif
643
550 644 ## render extra user menu
551 645 ${usermenu(active=(active=='my_account'))}
552 646
@@ -606,7 +700,7 b''
606 700
607 701 if(data){
608 702
609 tmpl += '<i class="icon-folder-close"></i> ';
703 tmpl += '<i class="icon-repo-group"></i> ';
610 704
611 705 }
612 706 tmpl += escapeMarkup(repoGroupName);
@@ -615,6 +709,22 b''
615 709 }(result, escapeMarkup);
616 710 };
617 711
712 var escapeRegExChars = function (value) {
713 return value.replace(/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g, "\\$&");
714 };
715
716 var getRepoIcon = function(repo_type) {
717 if (repo_type === 'hg') {
718 return '<i class="icon-hg"></i> ';
719 }
720 else if (repo_type === 'git') {
721 return '<i class="icon-git"></i> ';
722 }
723 else if (repo_type === 'svn') {
724 return '<i class="icon-svn"></i> ';
725 }
726 return ''
727 };
618 728
619 729 var autocompleteMainFilterFormatResult = function (data, value, org_formatter) {
620 730
@@ -623,38 +733,32 b''
623 733 }
624 734
625 735 var searchType = data['type'];
736 var searchSubType = data['subtype'];
626 737 var valueDisplay = data['value_display'];
627 738
628 var escapeRegExChars = function (value) {
629 return value.replace(/[\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|]/g, "\\$&");
630 };
631 739 var pattern = '(' + escapeRegExChars(value) + ')';
632 740
633 var getRepoIcon = function(repo_type) {
634 if (repo_type === 'hg') {
635 return '<i class="icon-hg"></i> ';
636 }
637 else if (repo_type === 'git') {
638 return '<i class="icon-git"></i> ';
639 }
640 else if (repo_type === 'svn') {
641 return '<i class="icon-svn"></i> ';
642 }
643 return ''
644 };
741 valueDisplay = Select2.util.escapeMarkup(valueDisplay);
645 742
646 743 // highlight match
647 valueDisplay = Select2.util.escapeMarkup(valueDisplay);
648 valueDisplay = valueDisplay.replace(new RegExp(pattern, 'gi'), '<strong>$1<\/strong>');
744 if (searchType != 'text') {
745 valueDisplay = valueDisplay.replace(new RegExp(pattern, 'gi'), '<strong>$1<\/strong>');
746 }
649 747
650 748 var icon = '';
651 749
652 750 if (searchType === 'hint') {
653 icon += '<i class="icon-folder-close"></i> ';
751 icon += '<i class="icon-repo-group"></i> ';
654 752 }
655 // full text search
753 // full text search/hints
656 754 else if (searchType === 'search') {
657 755 icon += '<i class="icon-more"></i> ';
756 if (searchSubType !== undefined && searchSubType == 'repo') {
757 valueDisplay += '<div class="pull-right tag">repository</div>';
758 }
759 else if (searchSubType !== undefined && searchSubType == 'repo_group') {
760 valueDisplay += '<div class="pull-right tag">repo group</div>';
761 }
658 762 }
659 763 // repository
660 764 else if (searchType === 'repo') {
@@ -671,12 +775,13 b''
671 775 }
672 776 // repository groups
673 777 else if (searchType === 'repo_group') {
674 icon += '<i class="icon-folder-close"></i> ';
778 icon += '<i class="icon-repo-group"></i> ';
675 779 }
676 780 // user group
677 781 else if (searchType === 'user_group') {
678 782 icon += '<i class="icon-group"></i> ';
679 783 }
784 // user
680 785 else if (searchType === 'user') {
681 786 icon += '<img class="gravatar" src="{0}"/>'.format(data['icon_link']);
682 787 }
@@ -690,6 +795,20 b''
690 795 icon += '<i class="icon-tag"></i>';
691 796 }
692 797 }
798 // file
799 else if (searchType === 'file') {
800 var repo_data = data['repo_data'];
801 var repoIcon = getRepoIcon(repo_data['repository_type']);
802 if (repoIcon) {
803 icon += repoIcon;
804 } else {
805 icon += '<i class="icon-tag"></i>';
806 }
807 }
808 // generic text
809 else if (searchType === 'text') {
810 icon = '';
811 }
693 812
694 813 var tmpl = '<div class="ac-container-wrap">{0}{1}</div>';
695 814 return tmpl.format(icon, valueDisplay);
@@ -699,25 +818,53 b''
699 818 if (suggestion.type === "hint") {
700 819 // we skip action
701 820 $('#main_filter').focus();
821 }
822 else if (suggestion.type === "text") {
823 // we skip action
824 $('#main_filter').focus();
825
702 826 } else {
703 827 window.location = suggestion['url'];
704 828 }
705 829 };
830
706 831 var autocompleteMainFilterResult = function (suggestion, originalQuery, queryLowerCase) {
707 832 if (queryLowerCase.split(':').length === 2) {
708 833 queryLowerCase = queryLowerCase.split(':')[1]
709 834 }
835 if (suggestion.type === "text") {
836 // special case we don't want to "skip" display for
837 return true
838 }
710 839 return suggestion.value_display.toLowerCase().indexOf(queryLowerCase) !== -1;
711 840 };
712 841
842 var cleanContext = {
843 repo_view_type: null,
844
845 repo_id: null,
846 repo_name: "",
847
848 repo_group_id: null,
849 repo_group_name: null
850 };
851 var removeGoToFilter = function () {
852 $('.searchTagHidable').hide();
853 $('#main_filter').autocomplete(
854 'setOptions', {params:{search_context: cleanContext}});
855 };
856
713 857 $('#main_filter').autocomplete({
714 858 serviceUrl: pyroutes.url('goto_switcher_data'),
715 params: {"search_context": templateContext.search_context},
859 params: {
860 "search_context": templateContext.search_context
861 },
716 862 minChars:2,
717 863 maxHeight:400,
718 864 deferRequestBy: 300, //miliseconds
719 865 tabDisabled: true,
720 autoSelectFirst: true,
866 autoSelectFirst: false,
867 containerClass: 'autocomplete-qfilter-suggestions',
721 868 formatResult: autocompleteMainFilterFormatResult,
722 869 lookupFilter: autocompleteMainFilterResult,
723 870 onSelect: function (element, suggestion) {
@@ -736,6 +883,18 b''
736 883 $('#main_filter_help').toggle();
737 884 };
738 885
886 $('#main_filter').on('keydown.autocomplete', function (e) {
887
888 var BACKSPACE = 8;
889 var el = $(e.currentTarget);
890 if(e.which === BACKSPACE){
891 var inputVal = el.val();
892 if (inputVal === ""){
893 removeGoToFilter()
894 }
895 }
896 });
897
739 898 </script>
740 899 <script src="${h.asset('js/rhodecode/base/keyboard-bindings.js', ver=c.rhodecode_version_hash)}"></script>
741 900 </%def>
@@ -7,7 +7,7 b" go_import_header = ''"
7 7 if hasattr(c, 'rhodecode_db_repo'):
8 8 c.template_context['repo_type'] = c.rhodecode_db_repo.repo_type
9 9 c.template_context['repo_landing_commit'] = c.rhodecode_db_repo.landing_rev[1]
10 ## check repo context
10 c.template_context['repo_id'] = c.rhodecode_db_repo.repo_id
11 11 c.template_context['repo_view_type'] = h.get_repo_view_type(request)
12 12
13 13 if getattr(c, 'repo_group', None):
@@ -29,6 +29,7 b" c.template_context['default_user'] = {"
29 29 c.template_context['search_context'] = {
30 30 'repo_group_id': c.template_context.get('repo_group_id'),
31 31 'repo_group_name': c.template_context.get('repo_group_name'),
32 'repo_id': c.template_context.get('repo_id'),
32 33 'repo_name': c.template_context.get('repo_name'),
33 34 'repo_view_type': c.template_context.get('repo_view_type'),
34 35 }
@@ -133,13 +133,13 b''
133 133
134 134 <div class="checkbox">
135 135 ${h.checkbox('extensions_evolve' + suffix, 'True', **kwargs)}
136 <label for="extensions_evolve${suffix}">${_('Enable evolve extension')}</label>
136 <label for="extensions_evolve${suffix}">${_('Enable Evolve and Topic extension')}</label>
137 137 </div>
138 138 <div class="label">
139 139 % if display_globals:
140 <span class="help-block">${_('Enable evolve extension for all repositories.')}</span>
140 <span class="help-block">${_('Enable Evolve and Topic extensions for all repositories.')}</span>
141 141 % else:
142 <span class="help-block">${_('Enable evolve extension for this repository.')}</span>
142 <span class="help-block">${_('Enable Evolve and Topic extensions for this repository.')}</span>
143 143 % endif
144 144 </div>
145 145
@@ -8,10 +8,7 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
13 <span id="obj_count">0</span> ${_('bookmarks')}
14 </%def>
11 <%def name="breadcrumbs_links()"></%def>
15 12
16 13 <%def name="menu_bar_nav()">
17 14 ${self.menu_items(active='repositories')}
@@ -24,7 +21,7 b''
24 21 <%def name="main()">
25 22 <div class="box">
26 23 <div class="title">
27 ${self.repo_page_title(c.rhodecode_db_repo)}
24
28 25 %if c.has_references:
29 26 <ul class="links">
30 27 <li>
@@ -33,7 +30,8 b''
33 30 </ul>
34 31 %endif
35 32 %if c.has_references:
36 ${self.breadcrumbs()}
33 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
34 <span id="obj_count">0</span> ${_('bookmarks')}
37 35 %endif
38 36 </div>
39 37 <table id="obj_list_table" class="display"></table>
@@ -8,10 +8,7 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
13 <span id="obj_count">0</span> ${_('branches')}
14 </%def>
11 <%def name="breadcrumbs_links()"></%def>
15 12
16 13 <%def name="menu_bar_nav()">
17 14 ${self.menu_items(active='repositories')}
@@ -24,7 +21,7 b''
24 21 <%def name="main()">
25 22 <div class="box">
26 23 <div class="title">
27 ${self.repo_page_title(c.rhodecode_db_repo)}
24
28 25 %if c.has_references:
29 26 <ul class="links">
30 27 <li>
@@ -33,7 +30,8 b''
33 30 </ul>
34 31 %endif
35 32 %if c.has_references:
36 ${self.breadcrumbs()}
33 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
34 <span id="obj_count">0</span> ${_('branches')}
37 35 %endif
38 36 </div>
39 37 <table id="obj_list_table" class="display"></table>
@@ -15,7 +15,7 b''
15 15 </%def>
16 16
17 17 <%def name="menu_bar_subnav()">
18 ${self.repo_menu(active='changelog')}
18 ${self.repo_menu(active='commits')}
19 19 </%def>
20 20
21 21 <%def name="main()">
@@ -25,119 +25,117 b''
25 25 templateContext.commit_data.commit_id = "${c.commit.raw_id}";
26 26 </script>
27 27 <div class="box">
28 <div class="title">
29 ${self.repo_page_title(c.rhodecode_db_repo)}
30 </div>
31 28
32 29 <div id="changeset_compare_view_content" class="summary changeset">
33 30 <div class="summary-detail">
34 <div class="summary-detail-header">
35 <div class="breadcrumbs files_location">
36 <h4>
37 ${_('Commit')}
31 <div class="fieldset">
32 <div class="left-label-summary">
33 <p>${_('Commit')}</p>
34 <div class="right-label-summary">
35 <code>
36 ${h.show_id(c.commit)}
37 </code>
38 <i class="tooltip icon-clipboard clipboard-action" data-clipboard-text="${c.commit.raw_id}" title="${_('Copy the full commit id')}"></i>
39 % if hasattr(c.commit, 'phase'):
40 <span class="tag phase-${c.commit.phase} tooltip" title="${_('Commit phase')}">${c.commit.phase}</span>
41 % endif
38 42
39 <code>
40 ${h.show_id(c.commit)}
41 </code>
42 <i class="tooltip icon-clipboard clipboard-action" data-clipboard-text="${c.commit.raw_id}" title="${_('Copy the full commit id')}"></i>
43 % if hasattr(c.commit, 'phase'):
44 <span class="tag phase-${c.commit.phase} tooltip" title="${_('Commit phase')}">${c.commit.phase}</span>
45 % endif
46
47 ## obsolete commits
48 % if hasattr(c.commit, 'obsolete'):
49 % if c.commit.obsolete:
50 <span class="tag obsolete-${c.commit.obsolete} tooltip" title="${_('Evolve State')}">${_('obsolete')}</span>
43 ## obsolete commits
44 % if hasattr(c.commit, 'obsolete'):
45 % if c.commit.obsolete:
46 <span class="tag obsolete-${c.commit.obsolete} tooltip" title="${_('Evolve State')}">${_('obsolete')}</span>
47 % endif
51 48 % endif
52 % endif
53 49
54 ## hidden commits
55 % if hasattr(c.commit, 'hidden'):
56 % if c.commit.hidden:
57 <span class="tag hidden-${c.commit.hidden} tooltip" title="${_('Evolve State')}">${_('hidden')}</span>
50 ## hidden commits
51 % if hasattr(c.commit, 'hidden'):
52 % if c.commit.hidden:
53 <span class="tag hidden-${c.commit.hidden} tooltip" title="${_('Evolve State')}">${_('hidden')}</span>
54 % endif
58 55 % endif
59 % endif
60 </h4>
56
61 57
58 <div class="pull-right">
59 <span id="parent_link">
60 <a href="#parentCommit" title="${_('Parent Commit')}"><i class="icon-left icon-no-margin"></i>${_('parent')}</a>
61 </span>
62 |
63 <span id="child_link">
64 <a href="#childCommit" title="${_('Child Commit')}">${_('child')}<i class="icon-right icon-no-margin"></i></a>
65 </span>
66 </div>
67
68 </div>
69 </div>
62 70 </div>
63 <div class="pull-right">
64 <span id="parent_link">
65 <a href="#parentCommit" title="${_('Parent Commit')}"><i class="icon-left icon-no-margin"></i>${_('parent')}</a>
66 </span>
67 |
68 <span id="child_link">
69 <a href="#childCommit" title="${_('Child Commit')}">${_('child')}<i class="icon-right icon-no-margin"></i></a>
70 </span>
71 </div>
72 </div>
71
72
73 73
74 74 <div class="fieldset">
75 <div class="left-label">
76 ${_('Description')}:
77 </div>
78 <div class="right-content">
79 <div id="trimmed_message_box" class="commit">${h.urlify_commit_message(c.commit.message,c.repo_name)}</div>
80 <div id="message_expand" style="display:none;">
81 ${_('Expand')}
75 <div class="left-label-summary">
76 <p>${_('Description')}:</p>
77 <div class="right-label-summary">
78 <div id="trimmed_message_box" class="commit">${h.urlify_commit_message(c.commit.message,c.repo_name)}</div>
79 <div id="message_expand" style="display:none;">
80 ${_('Expand')}
81 </div>
82 82 </div>
83 83 </div>
84 84 </div>
85 85
86 86 %if c.statuses:
87 87 <div class="fieldset">
88 <div class="left-label">
89 ${_('Commit status')}:
90 </div>
91 <div class="right-content">
92 <div class="changeset-status-ico">
93 <div class="${'flag_status %s' % c.statuses[0]} pull-left"></div>
88 <div class="left-label-summary">
89 <p>${_('Commit status')}:</p>
90 <div class="right-label-summary">
91 <div class="changeset-status-ico">
92 <div class="${'flag_status %s' % c.statuses[0]} pull-left"></div>
93 </div>
94 <div title="${_('Commit status')}" class="changeset-status-lbl">[${h.commit_status_lbl(c.statuses[0])}]</div>
94 95 </div>
95 <div title="${_('Commit status')}" class="changeset-status-lbl">[${h.commit_status_lbl(c.statuses[0])}]</div>
96 96 </div>
97 97 </div>
98 98 %endif
99 99
100 100 <div class="fieldset">
101 <div class="left-label">
102 ${_('References')}:
103 </div>
104 <div class="right-content">
105 <div class="tags">
106
107 %if c.commit.merge:
108 <span class="mergetag tag">
109 <i class="icon-merge"></i>${_('merge')}
110 </span>
111 %endif
101 <div class="left-label-summary">
102 <p>${_('References')}:</p>
103 <div class="right-label-summary">
104 <div class="tags">
105 %if c.commit.merge:
106 <span class="mergetag tag">
107 <i class="icon-merge"></i>${_('merge')}
108 </span>
109 %endif
112 110
113 %if h.is_hg(c.rhodecode_repo):
114 %for book in c.commit.bookmarks:
115 <span class="booktag tag" title="${h.tooltip(_('Bookmark %s') % book)}">
116 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=c.commit.raw_id,_query=dict(at=book))}"><i class="icon-bookmark"></i>${h.shorter(book)}</a>
117 </span>
118 %endfor
119 %endif
111 %if h.is_hg(c.rhodecode_repo):
112 %for book in c.commit.bookmarks:
113 <span class="booktag tag" title="${h.tooltip(_('Bookmark %s') % book)}">
114 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=c.commit.raw_id,_query=dict(at=book))}"><i class="icon-bookmark"></i>${h.shorter(book)}</a>
115 </span>
116 %endfor
117 %endif
120 118
121 %for tag in c.commit.tags:
122 <span class="tagtag tag" title="${h.tooltip(_('Tag %s') % tag)}">
123 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=c.commit.raw_id,_query=dict(at=tag))}"><i class="icon-tag"></i>${tag}</a>
124 </span>
125 %endfor
119 %for tag in c.commit.tags:
120 <span class="tagtag tag" title="${h.tooltip(_('Tag %s') % tag)}">
121 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=c.commit.raw_id,_query=dict(at=tag))}"><i class="icon-tag"></i>${tag}</a>
122 </span>
123 %endfor
126 124
127 %if c.commit.branch:
128 <span class="branchtag tag" title="${h.tooltip(_('Branch %s') % c.commit.branch)}">
129 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=c.commit.raw_id,_query=dict(at=c.commit.branch))}"><i class="icon-code-fork"></i>${h.shorter(c.commit.branch)}</a>
130 </span>
131 %endif
125 %if c.commit.branch:
126 <span class="branchtag tag" title="${h.tooltip(_('Branch %s') % c.commit.branch)}">
127 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=c.commit.raw_id,_query=dict(at=c.commit.branch))}"><i class="icon-code-fork"></i>${h.shorter(c.commit.branch)}</a>
128 </span>
129 %endif
130 </div>
132 131 </div>
133 </div>
134 132 </div>
133 </div>
135 134
136 135 <div class="fieldset">
137 <div class="left-label">
138 ${_('Diff options')}:
139 </div>
140 <div class="right-content">
136 <div class="left-label-summary">
137 <p>${_('Diff options')}:</p>
138 <div class="right-label-summary">
141 139 <div class="diff-actions">
142 140 <a href="${h.route_path('repo_commit_raw',repo_name=c.repo_name,commit_id=c.commit.raw_id)}" class="tooltip" title="${h.tooltip(_('Raw diff'))}">
143 141 ${_('Raw Diff')}
@@ -151,14 +149,14 b''
151 149 ${_('Download Diff')}
152 150 </a>
153 151 </div>
152 </div>
154 153 </div>
155 154 </div>
156 155
157 156 <div class="fieldset">
158 <div class="left-label">
159 ${_('Comments')}:
160 </div>
161 <div class="right-content">
157 <div class="left-label-summary">
158 <p>${_('Comments')}:</p>
159 <div class="right-label-summary">
162 160 <div class="comments-number">
163 161 %if c.comments:
164 162 <a href="#comments">${_ungettext("%d Commit comment", "%d Commit comments", len(c.comments)) % len(c.comments)}</a>,
@@ -171,40 +169,42 b''
171 169 ${_ungettext("%d Inline Comment", "%d Inline Comments", c.inline_cnt) % c.inline_cnt}
172 170 %endif
173 171 </div>
172 </div>
174 173 </div>
175 174 </div>
176 175
177 176 <div class="fieldset">
178 <div class="left-label">
179 ${_('Unresolved TODOs')}:
180 </div>
181 <div class="right-content">
182 <div class="comments-number">
183 % if c.unresolved_comments:
184 % for co in c.unresolved_comments:
185 <a class="permalink" href="#comment-${co.comment_id}" onclick="Rhodecode.comments.scrollToComment($('#comment-${co.comment_id}'))"> #${co.comment_id}</a>${'' if loop.last else ','}
186 % endfor
187 % else:
188 ${_('There are no unresolved TODOs')}
189 % endif
190 </div>
177 <div class="left-label-summary">
178 <p>${_('Unresolved TODOs')}:</p>
179 <div class="right-label-summary">
180 <div class="comments-number">
181 % if c.unresolved_comments:
182 % for co in c.unresolved_comments:
183 <a class="permalink" href="#comment-${co.comment_id}" onclick="Rhodecode.comments.scrollToComment($('#comment-${co.comment_id}'))"> #${co.comment_id}</a>${'' if loop.last else ','}
184 % endfor
185 % else:
186 ${_('There are no unresolved TODOs')}
187 % endif
188 </div>
189 </div>
191 190 </div>
192 191 </div>
193 192
194 </div> <!-- end summary-detail -->
193 <div class="fieldset">
194 <div class="left-label-summary">
195 <p>${_('Author')}</p>
195 196
196 <div id="commit-stats" class="sidebar-right">
197 <div class="summary-detail-header">
198 <h4 class="item">
199 ${_('Author')}
200 </h4>
201 </div>
202 <div class="sidebar-right-content">
197 <div class="right-label-summary">
203 198 ${self.gravatar_with_user(c.commit.author)}
204 199 <div class="user-inline-data">- ${h.age_component(c.commit.date)}</div>
200 </div>
205 201 </div>
206 </div><!-- end sidebar -->
202
203 <div class="clear-fix"></div>
204
205 </div> <!-- end summary-detail -->
207 206 </div> <!-- end summary -->
207 </div>
208 208 <div class="cs_files">
209 209 <%namespace name="cbdiffs" file="/codeblocks/diffs.mako"/>
210 210 ${cbdiffs.render_diffset_menu(c.changes[c.commit.raw_id])}
@@ -139,7 +139,7 b''
139 139 ## only super-admin, repo admin OR comment owner can delete, also hide delete if currently viewed comment is outdated
140 140 %if not outdated_at_ver and (not comment.pull_request or (comment.pull_request and not comment.pull_request.is_closed())):
141 141 ## permissions to delete
142 %if h.HasPermissionAny('hg.admin')() or h.HasRepoPermissionAny('repository.admin')(c.repo_name) or comment.author.user_id == c.rhodecode_user.user_id:
142 %if c.is_super_admin or h.HasRepoPermissionAny('repository.admin')(c.repo_name) or comment.author.user_id == c.rhodecode_user.user_id:
143 143 ## TODO: dan: add edit comment here
144 144 <a onclick="return Rhodecode.comments.deleteComment(this);" class="delete-comment"> ${_('Delete')}</a>
145 145 %else:
@@ -12,67 +12,76 b''
12 12 %endif
13 13 </%def>
14 14
15 <%def name="breadcrumbs_links()">
16 ${_('Commits')} -
17 r${c.commit_ranges[0].idx}:${h.short_id(c.commit_ranges[0].raw_id)}
18 ...
19 r${c.commit_ranges[-1].idx}:${h.short_id(c.commit_ranges[-1].raw_id)}
20 ${_ungettext('(%s commit)','(%s commits)', len(c.commit_ranges)) % len(c.commit_ranges)}
21 </%def>
15 <%def name="breadcrumbs_links()"></%def>
22 16
23 17 <%def name="menu_bar_nav()">
24 18 ${self.menu_items(active='repositories')}
25 19 </%def>
26 20
27 21 <%def name="menu_bar_subnav()">
28 ${self.repo_menu(active='changelog')}
22 ${self.repo_menu(active='commits')}
29 23 </%def>
30 24
31 25 <%def name="main()">
32 <div class="summary-header">
33 <div class="title">
34 ${self.repo_page_title(c.rhodecode_db_repo)}
35 </div>
36 </div>
37
26 <div class="box">
27 <div class="summary changeset">
28 <div class="summary-detail">
29 <div class="summary-detail-header">
30 <span class="breadcrumbs files_location">
31 <h4>
32 ${_('Commit Range')}
33 </h4>
34 </span>
38 35
39 <div class="summary changeset">
40 <div class="summary-detail">
41 <div class="summary-detail-header">
42 <span class="breadcrumbs files_location">
43 <h4>
44 ${_('Commit Range')}
45 <code>
46 r${c.commit_ranges[0].idx}:${h.short_id(c.commit_ranges[0].raw_id)}...r${c.commit_ranges[-1].idx}:${h.short_id(c.commit_ranges[-1].raw_id)}
47 </code>
48 </h4>
49 </span>
50 </div>
36 <div class="clear-fix"></div>
37 </div>
51 38
52 <div class="fieldset">
53 <div class="left-label">
54 ${_('Diff option')}:
55 </div>
56 <div class="right-content">
57 <div class="btn btn-primary">
58 <a href="${h.route_path('repo_compare',
59 repo_name=c.repo_name,
60 source_ref_type='rev',
61 source_ref=getattr(c.commit_ranges[0].parents[0] if c.commit_ranges[0].parents else h.EmptyCommit(), 'raw_id'),
62 target_ref_type='rev',
63 target_ref=c.commit_ranges[-1].raw_id)}"
64 >
65 ${_('Show combined compare')}
66 </a>
39 <div class="fieldset">
40 <div class="left-label-summary">
41 <p class="spacing">${_('Range')}:</p>
42 <div class="right-label-summary">
43 <div class="code-header" >
44 <div class="compare_header">
45 <code class="fieldset-text-line">
46 r${c.commit_ranges[0].idx}:${h.short_id(c.commit_ranges[0].raw_id)}
47 ...
48 r${c.commit_ranges[-1].idx}:${h.short_id(c.commit_ranges[-1].raw_id)}
49 ${_ungettext('(%s commit)','(%s commits)', len(c.commit_ranges)) % len(c.commit_ranges)}
50 </code>
51 </div>
52 </div>
53 </div>
54 </div>
67 55 </div>
68 </div>
69 </div>
70 56
71 </div> <!-- end summary-detail -->
57 <div class="fieldset">
58 <div class="left-label-summary">
59 <p class="spacing">${_('Diff Option')}:</p>
60 <div class="right-label-summary">
61 <div class="code-header" >
62 <div class="compare_header">
63 <div class="btn btn-primary">
64 <a href="${h.route_path('repo_compare',
65 repo_name=c.repo_name,
66 source_ref_type='rev',
67 source_ref=getattr(c.commit_ranges[0].parents[0] if c.commit_ranges[0].parents else h.EmptyCommit(), 'raw_id'),
68 target_ref_type='rev',
69 target_ref=c.commit_ranges[-1].raw_id)}"
70 >
71 ${_('Show combined diff')}
72 </a>
73 </div>
74 </div>
75 </div>
76 </div>
77 </div>
78 </div>
72 79
73 </div> <!-- end summary -->
80 <div class="clear-fix"></div>
81 </div> <!-- end summary-detail -->
82 </div> <!-- end summary -->
74 83
75 <div id="changeset_compare_view_content">
84 <div id="changeset_compare_view_content">
76 85 <div class="pull-left">
77 86 <div class="btn-group">
78 87 <a
@@ -105,4 +114,6 b''
105 114 %endfor
106 115 </div>
107 116 </div>
117 </div>
118
108 119 </%def>
@@ -959,7 +959,8 b' def get_comments_for(diff_type, comments'
959 959 text: _gettext('Toggle Wide Mode diff'),
960 960 action: function () {
961 961 updateSticky();
962 Rhodecode.comments.toggleWideMode(this);
962 var wide = Rhodecode.comments.toggleWideMode(this);
963 storeUserSessionAttr('rc_user_session_attr.wide_diff_mode', wide);
963 964 return null;
964 965 },
965 966 url: null,
@@ -1002,6 +1003,11 b' def get_comments_for(diff_type, comments'
1002 1003 ]
1003 1004 };
1004 1005
1006 // get stored diff mode and pre-enable it
1007 if (templateContext.session_attrs.wide_diff_mode === "true") {
1008 Rhodecode.comments.toggleWideMode(null);
1009 }
1010
1005 1011 $("#diff_menu").select2({
1006 1012 minimumResultsForSearch: -1,
1007 1013 containerCssClass: "drop-menu",
@@ -23,17 +23,36 b''
23 23 </%def>
24 24
25 25 <%def name="menu_bar_subnav()">
26 ${self.repo_menu(active='changelog')}
26 ${self.repo_menu(active='commits')}
27 27 </%def>
28 28
29 29 <%def name="main()">
30 30
31 31 <div class="box">
32
32 33 <div class="title">
33 ${self.repo_page_title(c.rhodecode_db_repo)}
34 <div id="filter_changelog">
35 ${h.hidden('branch_filter')}
36 %if c.selected_name:
37 <div class="btn btn-default" id="clear_filter" >
38 ${_('Clear filter')}
39 </div>
40 %endif
41 </div>
42 <div class="pull-left obsolete-toggle">
43 % if h.is_hg(c.rhodecode_repo):
44 % if c.show_hidden:
45 <a class="action-link" href="${h.current_route_path(request, evolve=0)}">${_('Hide obsolete/hidden')}</a>
46 % else:
47 <a class="action-link" href="${h.current_route_path(request, evolve=1)}">${_('Show obsolete/hidden')}</a>
48 % endif
49 % else:
50 <span class="action-link disabled">${_('Show hidden')}</span>
51 % endif
52 </div>
34 53 <ul class="links">
35 54 <li>
36 <a href="#" class="btn btn-small" id="rev_range_container" style="display:none;"></a>
55
37 56 %if c.rhodecode_db_repo.fork:
38 57 <span>
39 58 <a id="compare_fork_button"
@@ -61,11 +80,6 b''
61 80 </span>
62 81 %endif
63 82
64 ## clear selection
65 <div title="${_('Clear selection')}" class="btn" id="rev_range_clear" style="display:none">
66 ${_('Clear selection')}
67 </div>
68
69 83 </li>
70 84 </ul>
71 85 </div>
@@ -74,29 +88,7 b''
74 88 <script type="text/javascript" src="${h.asset('js/src/plugins/jquery.commits-graph.js')}"></script>
75 89
76 90 <div class="graph-header">
77 <div id="filter_changelog">
78 ${h.hidden('branch_filter')}
79 %if c.selected_name:
80 <div class="btn btn-default" id="clear_filter" >
81 ${_('Clear filter')}
82 </div>
83 %endif
84 </div>
85 91 ${self.breadcrumbs('breadcrumbs_light')}
86 <div class="pull-right">
87 % if h.is_hg(c.rhodecode_repo):
88 % if c.show_hidden:
89 <a class="action-link" href="${h.current_route_path(request, evolve=0)}">${_('Hide obsolete/hidden')}</a>
90 % else:
91 <a class="action-link" href="${h.current_route_path(request, evolve=1)}">${_('Show obsolete/hidden')}</a>
92 % endif
93 % else:
94 <span class="action-link disabled">${_('Show hidden')}</span>
95 % endif
96 </div>
97 <div id="commit-counter" data-total=${c.total_cs} class="pull-right">
98 ${_ungettext('showing %d out of %d commit', 'showing %d out of %d commits', c.showing_commits) % (c.showing_commits, c.total_cs)}
99 </div>
100 92 </div>
101 93
102 94 <div id="graph">
@@ -104,18 +96,21 b''
104 96 <div id="graph_nodes">
105 97 <div id="graph_canvas"></div>
106 98 </div>
107 <div id="graph_content" class="main-content graph_full_width">
99 <div id="graph_content" class="graph_full_width">
108 100
109 101 <div class="table">
110 102 <table id="changesets" class="rctable">
111 103 <tr>
112 104 ## checkbox
113 <th></th>
114 <th colspan="2"></th>
105 <th colspan="4">
106 ## clear selection
107 <div title="${_('Clear selection')}" class="btn btn-sm" id="rev_range_clear" style="display:none">
108 <i class="icon-cancel-circled2"></i>
109 </div>
110 <div class="btn btn-sm disabled" disabled="disabled" id="rev_range_more" style="display:none;">${_('Select second commit')}</div>
111 <a href="#" class="btn btn-success btn-sm" id="rev_range_container" style="display:none;"></a>
112 </th>
115 113
116 <th>${_('Commit')}</th>
117 ## Mercurial phase/evolve state
118 <th></th>
119 114 ## commit message expand arrow
120 115 <th></th>
121 116 <th>${_('Commit Message')}</th>
@@ -124,6 +119,8 b''
124 119 <th>${_('Author')}</th>
125 120
126 121 <th>${_('Refs')}</th>
122 ## comments
123 <th></th>
127 124 </tr>
128 125
129 126 <tbody class="commits-range">
@@ -135,6 +132,9 b''
135 132 <div class="pagination-wh pagination-left">
136 133 ${c.pagination.pager('$link_previous ~2~ $link_next')}
137 134 </div>
135 <div id="commit-counter" data-total=${c.total_cs} class="pull-right">
136 ${_ungettext('showing %d out of %d commit', 'showing %d out of %d commits', c.showing_commits) % (c.showing_commits, c.total_cs)}
137 </div>
138 138 </div>
139 139
140 140 <script type="text/javascript">
@@ -144,6 +144,7 b''
144 144 // Create links to commit ranges when range checkboxes are selected
145 145 var $commitCheckboxes = $('.commit-range');
146 146 // cache elements
147 var $commitRangeMore = $('#rev_range_more');
147 148 var $commitRangeContainer = $('#rev_range_container');
148 149 var $commitRangeClear = $('#rev_range_clear');
149 150
@@ -155,57 +156,68 b''
155 156 }
156 157 }
157 158 var open_new_pull_request = $('#open_new_pull_request');
158 if(open_new_pull_request){
159 var selected_changes = selectedCheckboxes.length;
160 if (selected_changes > 1 || selected_changes == 1 && templateContext.repo_type == 'svn') {
161 open_new_pull_request.hide();
162 } else {
163 if (selected_changes == 1) {
164 open_new_pull_request.html(_gettext('Open new pull request for selected commit'));
165 } else if (selected_changes == 0) {
166 open_new_pull_request.html(_gettext('Open new pull request'));
167 }
168 open_new_pull_request.show();
169 }
159
160 if (open_new_pull_request) {
161 var selected_changes = selectedCheckboxes.length;
162 open_new_pull_request.hide();
163 if (selected_changes == 1) {
164 open_new_pull_request.html(_gettext('Open new pull request for selected commit'));
165 } else {
166 open_new_pull_request.html(_gettext('Open new pull request'));
167 }
168 open_new_pull_request.show();
170 169 }
171 170
172 if (selectedCheckboxes.length>0){
173 var revEnd = selectedCheckboxes[0].name;
174 var revStart = selectedCheckboxes[selectedCheckboxes.length-1].name;
175 var url = pyroutes.url('repo_commit',
176 {'repo_name': '${c.repo_name}',
177 'commit_id': revStart+'...'+revEnd});
171 if (selectedCheckboxes.length > 0) {
172 $('#compare_fork_button').hide();
173 var commitStart = $(selectedCheckboxes[selectedCheckboxes.length-1]).data();
174
175 var revStart = commitStart.commitId;
176
177 var commitEnd = $(selectedCheckboxes[0]).data();
178 var revEnd = commitEnd.commitId;
178 179
179 var link = (revStart == revEnd)
180 ? _gettext('Show selected commit __S')
181 : _gettext('Show selected commits __S ... __E');
180 var lbl_start = '{0}'.format(commitStart.commitIdx, commitStart.shortId);
181 var lbl_end = '{0}'.format(commitEnd.commitIdx, commitEnd.shortId);
182
183 var url = pyroutes.url('repo_commit', {'repo_name': '${c.repo_name}', 'commit_id': revStart+'...'+revEnd});
184 var link = _gettext('Show commit range {0} ... {1}').format(lbl_start, lbl_end);
185
186 if (selectedCheckboxes.length > 1) {
187 $commitRangeClear.show();
188 $commitRangeMore.hide();
182 189
183 link = link.replace('__S', revStart.substr(0,6));
184 link = link.replace('__E', revEnd.substr(0,6));
190 $commitRangeContainer
191 .attr('href',url)
192 .html(link)
193 .show();
194
185 195
186 $commitRangeContainer
187 .attr('href',url)
188 .html(link)
189 .show();
196 } else {
197 $commitRangeContainer.hide();
198 $commitRangeClear.show();
199 $commitRangeMore.show();
200 }
190 201
191 $commitRangeClear.show();
192 var _url = pyroutes.url('pullrequest_new',
193 {'repo_name': '${c.repo_name}',
194 'commit': revEnd});
195 open_new_pull_request.attr('href', _url);
196 $('#compare_fork_button').hide();
202 // pull-request link
203 if (selectedCheckboxes.length == 1){
204 var _url = pyroutes.url('pullrequest_new', {'repo_name': '${c.repo_name}', 'commit': revEnd});
205 open_new_pull_request.attr('href', _url);
206 } else {
207 var _url = pyroutes.url('pullrequest_new', {'repo_name': '${c.repo_name}'});
208 open_new_pull_request.attr('href', _url);
209 }
210
197 211 } else {
198 212 $commitRangeContainer.hide();
199 213 $commitRangeClear.hide();
214 $commitRangeMore.hide();
200 215
201 216 %if c.branch_name:
202 var _url = pyroutes.url('pullrequest_new',
203 {'repo_name': '${c.repo_name}',
204 'branch':'${c.branch_name}'});
217 var _url = pyroutes.url('pullrequest_new', {'repo_name': '${c.repo_name}', 'branch':'${c.branch_name}'});
205 218 open_new_pull_request.attr('href', _url);
206 219 %else:
207 var _url = pyroutes.url('pullrequest_new',
208 {'repo_name': '${c.repo_name}'});
220 var _url = pyroutes.url('pullrequest_new', {'repo_name': '${c.repo_name}'});
209 221 open_new_pull_request.attr('href', _url);
210 222 %endif
211 223 $('#compare_fork_button').show();
@@ -241,13 +253,13 b''
241 253
242 254 $("#clear_filter").on("click", function() {
243 255 var filter = {'repo_name': '${c.repo_name}'};
244 window.location = pyroutes.url('repo_changelog', filter);
256 window.location = pyroutes.url('repo_commits', filter);
245 257 });
246 258
247 259 $("#branch_filter").select2({
248 260 'dropdownAutoWidth': true,
249 261 'width': 'resolve',
250 'placeholder': "${c.selected_name or _('Filter changelog')}",
262 'placeholder': "${c.selected_name or _('Branch filter')}",
251 263 containerCssClass: "drop-menu",
252 264 dropdownCssClass: "drop-menu-dropdown",
253 265 query: function(query){
@@ -295,7 +307,7 b''
295 307 else if (data.type == 'book'){
296 308 filter["bookmark"] = selected;
297 309 }
298 window.location = pyroutes.url('repo_changelog', filter);
310 window.location = pyroutes.url('repo_commits', filter);
299 311 });
300 312
301 313 commitsController = new CommitsController();
@@ -3,7 +3,7 b''
3 3
4 4 % if c.prev_page:
5 5 <tr>
6 <td colspan="9" class="load-more-commits">
6 <td colspan="10" class="load-more-commits">
7 7 <a class="prev-commits" href="#loadPrevCommits" onclick="commitsController.loadPrev(this, ${c.prev_page}, '${c.branch_name}', '${c.commit_id}', '${c.f_path}');return false">
8 8 ${_('load previous')}
9 9 </a>
@@ -21,10 +21,14 b''
21 21 <tr id="sha_${commit.raw_id}" class="changelogRow container ${'tablerow%s' % (cnt%2)}">
22 22
23 23 <td class="td-checkbox">
24 ${h.checkbox(commit.raw_id,class_="commit-range")}
24 ${h.checkbox(commit.raw_id,class_="commit-range", **{'data-commit-idx':commit.idx, 'data-commit-id': commit.raw_id, 'data-short-id': commit.short_id})}
25 25 </td>
26 ##
27 <td class="td-graphbox">
28
29 </td>
30
26 31 <td class="td-status">
27
28 32 %if c.statuses.get(commit.raw_id):
29 33 <div class="changeset-status-ico">
30 34 %if c.statuses.get(commit.raw_id)[2]:
@@ -41,44 +45,38 b''
41 45 <div class="tooltip flag_status not_reviewed" title="${_('Commit status: Not Reviewed')}"></div>
42 46 %endif
43 47 </td>
44 <td class="td-comments comments-col">
45 %if c.comments.get(commit.raw_id):
46 <a title="${_('Commit has comments')}" href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=commit.raw_id,_anchor='comment-%s' % c.comments[commit.raw_id][0].comment_id)}">
47 <i class="icon-comment"></i> ${len(c.comments[commit.raw_id])}
48 </a>
49 %endif
50 </td>
48
51 49 <td class="td-hash">
52 50 <code>
53 51
54 52 <a href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=commit.raw_id)}">
55 53 <span class="${'commit_hash obsolete' if getattr(commit, 'obsolete', None) else 'commit_hash'}">${h.show_id(commit)}</span>
56 54 </a>
55
57 56 <i class="tooltip icon-clipboard clipboard-action" data-clipboard-text="${commit.raw_id}" title="${_('Copy the full commit id')}"></i>
58 </code>
59 </td>
60 <td class="td-tags tags-col">
61 ## phase
57
58 ## COMMIT PHASES
59
60 ## Draft
62 61 % if hasattr(commit, 'phase'):
63 62 % if commit.phase != 'public':
64 <span class="tag phase-${commit.phase} tooltip" title="${_('Commit phase')}">${commit.phase}</span>
63 <span class="tag phase-${commit.phase} tooltip" title="${_('{} commit phase').format(commit.phase)}">${commit.phase[0].upper()}</span>
65 64 % endif
66 65 % endif
67 66
68 67 ## obsolete commits
69 % if hasattr(commit, 'obsolete'):
70 % if commit.obsolete:
71 <span class="tag obsolete-${commit.obsolete} tooltip" title="${_('Evolve State')}">${_('obsolete')}</span>
72 % endif
68 % if hasattr(commit, 'obsolete') and commit.obsolete:
69 <span class="tag obsolete-${commit.obsolete} tooltip" title="${_('Obsolete Evolve State')}">O</span>
73 70 % endif
74 71
75 72 ## hidden commits
76 % if hasattr(commit, 'hidden'):
77 % if commit.hidden:
78 <span class="tag obsolete-${commit.hidden} tooltip" title="${_('Evolve State')}">${_('hidden')}</span>
79 % endif
73 % if hasattr(commit, 'hidden') and commit.hidden:
74 <span class="tag obsolete-${commit.hidden} tooltip" title="${_('Hidden Evolve State')}">H</span>
80 75 % endif
76
77 </code>
81 78 </td>
79
82 80 <td class="td-message expand_commit" data-commit-id="${commit.raw_id}" title="${_('Expand commit message')}" onclick="commitsController.expandCommit(this, true); return false">
83 81 <i class="icon-expand-linked"></i>&nbsp;
84 82 </td>
@@ -108,7 +106,7 b''
108 106 ## branch
109 107 %if commit.branch:
110 108 <span class="tag branchtag" title="${h.tooltip(_('Branch %s') % commit.branch)}">
111 <a href="${h.route_path('repo_changelog',repo_name=c.repo_name,_query=dict(branch=commit.branch))}"><i class="icon-code-fork"></i>${h.shorter(commit.branch)}</a>
109 <a href="${h.route_path('repo_commits',repo_name=c.repo_name,_query=dict(branch=commit.branch))}"><i class="icon-code-fork"></i>${h.shorter(commit.branch)}</a>
112 110 </span>
113 111 %endif
114 112
@@ -130,6 +128,18 b''
130 128
131 129 </div>
132 130 </td>
131
132 <td class="td-comments comments-col">
133 <% cs_comments = c.comments.get(commit.raw_id,[]) %>
134 % if cs_comments:
135 <a title="${_('Commit has comments')}" href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=commit.raw_id,_anchor='comment-%s' % cs_comments[0].comment_id)}">
136 <i class="icon-comment"></i> ${len(cs_comments)}
137 </a>
138 % else:
139 <i class="icon-comment"></i> ${len(cs_comments)}
140 % endif
141 </td>
142
133 143 </tr>
134 144 % endfor
135 145
@@ -3,7 +3,7 b''
3 3
4 4 <table class="table rctable file_history">
5 5 %for cnt,cs in enumerate(c.pagination):
6 <tr id="chg_${cnt+1}" class="${'tablerow%s' % (cnt%2)}">
6 <tr id="chg_${cnt+1}" class="${('tablerow%s' % (cnt%2))}">
7 7 <td class="td-user">
8 8 ${base.gravatar_with_user(cs.author, 16)}
9 9 </td>
@@ -33,7 +33,19 b''
33 33 ${_('Show File')}
34 34 </a>
35 35 </td>
36 <td class="td-actions">
37 <a href="${h.route_path('repo_compare',repo_name=c.repo_name, source_ref_type="rev", source_ref=cs.raw_id,target_ref_type="rev", target_ref=c.commit_id,_query=dict(merge='1',f_path=c.changelog_for_path))}">
38 <span title="${'Diff {} vs {}'.format(cs.raw_id[:8],c.commit_id[:8])}">${_('Diff File')}</span>
39 </a>
40 </td>
36 41 </tr>
37 42 %endfor
43 <tr>
44 <td colspan="6">
45 <a id="file_history_overview_full" href="${h.route_path('repo_commits_file',repo_name=c.repo_name, commit_id=c.commit_id, f_path=c.f_path)}">
46 ${_('Show Full History')}
47 </a>
48 </td>
49 </tr>
38 50 </table>
39 51 </div>
@@ -13,9 +13,7 b''
13 13 %endif
14 14 </%def>
15 15
16 <%def name="breadcrumbs_links()">
17 ${_ungettext('%s commit','%s commits', len(c.commit_ranges)) % len(c.commit_ranges)}
18 </%def>
16 <%def name="breadcrumbs_links()"></%def>
19 17
20 18 <%def name="menu_bar_nav()">
21 19 ${self.menu_items(active='repositories')}
@@ -32,10 +30,6 b''
32 30 </script>
33 31
34 32 <div class="box">
35 <div class="title">
36 ${self.repo_page_title(c.rhodecode_db_repo)}
37 </div>
38
39 33 <div class="summary changeset">
40 34 <div class="summary-detail">
41 35 <div class="summary-detail-header">
@@ -43,24 +37,24 b''
43 37 <h4>
44 38 ${_('Compare Commits')}
45 39 % if c.file_path:
46 ${_('for file')} <a href="#${'a_' + h.FID('',c.file_path)}">${c.file_path}</a>
40 ${_('for file')} <a href="#${('a_' + h.FID('',c.file_path))}">${c.file_path}</a>
47 41 % endif
48 42
49 43 % if c.commit_ranges:
50 44 <code>
51 r${c.source_commit.idx}:${h.short_id(c.source_commit.raw_id)}...r${c.target_commit.idx}:${h.short_id(c.target_commit.raw_id)}
45 r${c.commit_ranges[0].idx}:${h.short_id(c.commit_ranges[0].raw_id)}...r${c.commit_ranges[-1].idx}:${h.short_id(c.commit_ranges[-1].raw_id)}
52 46 </code>
53 47 % endif
54 48 </h4>
55 49 </span>
50
51 <div class="clear-fix"></div>
56 52 </div>
57 53
58 54 <div class="fieldset">
59 <div class="left-label">
60 ${_('Target')}:
61 </div>
62 <div class="right-content">
63 <div>
55 <div class="left-label-summary">
56 <p class="spacing">${_('Target')}:</p>
57 <div class="right-label-summary">
64 58 <div class="code-header" >
65 59 <div class="compare_header">
66 60 ## The hidden elements are replaced with a select2 widget
@@ -72,11 +66,9 b''
72 66 </div>
73 67
74 68 <div class="fieldset">
75 <div class="left-label">
76 ${_('Source')}:
77 </div>
78 <div class="right-content">
79 <div>
69 <div class="left-label-summary">
70 <p class="spacing">${_('Source')}:</p>
71 <div class="right-label-summary">
80 72 <div class="code-header" >
81 73 <div class="compare_header">
82 74 ## The hidden elements are replaced with a select2 widget
@@ -88,17 +80,29 b''
88 80 </div>
89 81
90 82 <div class="fieldset">
91 <div class="left-label">
92 ${_('Actions')}:
93 </div>
94 <div class="right-content">
95 <div>
83 <div class="left-label-summary">
84 <p class="spacing">${_('Actions')}:</p>
85 <div class="right-label-summary">
96 86 <div class="code-header" >
97 87 <div class="compare_header">
98
99 88 <div class="compare-buttons">
100 89 % if c.compare_home:
101 90 <a id="compare_revs" class="btn btn-primary"> ${_('Compare Commits')}</a>
91 %if c.rhodecode_db_repo.fork:
92
93 <a class="btn btn-default" title="${h.tooltip(_('Compare fork with %s' % c.rhodecode_db_repo.fork.repo_name))}"
94 href="${h.route_path('repo_compare',
95 repo_name=c.rhodecode_db_repo.fork.repo_name,
96 source_ref_type=c.rhodecode_db_repo.landing_rev[0],
97 source_ref=c.rhodecode_db_repo.landing_rev[1],
98 target_repo=c.repo_name,target_ref_type='branch' if request.GET.get('branch') else c.rhodecode_db_repo.landing_rev[0],
99 target_ref=request.GET.get('branch') or c.rhodecode_db_repo.landing_rev[1],
100 _query=dict(merge=1))}"
101 >
102 ${_('Compare with origin')}
103 </a>
104
105 %endif
102 106
103 107 <a class="btn disabled tooltip" disabled="disabled" title="${_('Action unavailable in current view')}">${_('Swap')}</a>
104 108 <a class="btn disabled tooltip" disabled="disabled" title="${_('Action unavailable in current view')}">${_('Comment')}</a>
@@ -126,31 +130,31 b''
126 130 </div>
127 131 </div>
128 132 </div>
129 </div>
133 </div>
130 134 </div>
131 135
132 136 ## commit status form
133 137 <div class="fieldset" id="compare_changeset_status" style="display: none; margin-bottom: -80px;">
134 <div class="left-label">
135 ${_('Commit status')}:
136 </div>
137 <div class="right-content">
138 <%namespace name="comment" file="/changeset/changeset_file_comment.mako"/>
139 ## main comment form and it status
140 <%
141 def revs(_revs):
142 form_inputs = []
143 for cs in _revs:
144 tmpl = '<input type="hidden" data-commit-id="%(cid)s" name="commit_ids" value="%(cid)s">' % {'cid': cs.raw_id}
145 form_inputs.append(tmpl)
146 return form_inputs
147 %>
148 <div>
149 ${comment.comments(h.route_path('repo_commit_comment_create', repo_name=c.repo_name, commit_id='0'*16), None, is_compare=True, form_extras=revs(c.commit_ranges))}
138 <div class="left-label-summary">
139 <p class="spacing">${_('Commit status')}:</p>
140 <div class="right-label-summary">
141 <%namespace name="comment" file="/changeset/changeset_file_comment.mako"/>
142 ## main comment form and it status
143 <%
144 def revs(_revs):
145 form_inputs = []
146 for cs in _revs:
147 tmpl = '<input type="hidden" data-commit-id="%(cid)s" name="commit_ids" value="%(cid)s">' % {'cid': cs.raw_id}
148 form_inputs.append(tmpl)
149 return form_inputs
150 %>
151 <div>
152 ${comment.comments(h.route_path('repo_commit_comment_create', repo_name=c.repo_name, commit_id='0'*16), None, is_compare=True, form_extras=revs(c.commit_ranges))}
153 </div>
150 154 </div>
151 155 </div>
152 156 </div>
153
157 <div class="clear-fix"></div>
154 158 </div> <!-- end summary-detail -->
155 159 </div> <!-- end summary -->
156 160
@@ -275,8 +279,6 b''
275 279
276 280 ## table diff data
277 281 <div class="table">
278
279
280 282 % if not c.compare_home:
281 283 <div id="changeset_compare_view_content">
282 284 <div class="pull-left">
@@ -48,8 +48,8 b''
48 48 </a>
49 49 </li>
50 50 <li>
51 <a title="${_('Changelog')}" href="${h.route_path('repo_changelog',repo_name=repo_name)}">
52 <span>${_('Changelog')}</span>
51 <a title="${_('Commits')}" href="${h.route_path('repo_commits',repo_name=repo_name)}">
52 <span>${_('Commits')}</span>
53 53 </a>
54 54 </li>
55 55 <li>
@@ -205,7 +205,7 b''
205 205 <%def name="repo_group_name(repo_group_name, children_groups=None)">
206 206 <div>
207 207 <a href="${h.route_path('repo_group_home', repo_group_name=repo_group_name)}">
208 <i class="icon-folder-close" title="${_('Repository group')}" style="font-size: 16px"></i>
208 <i class="icon-repo-group" title="${_('Repository group')}" style="font-size: 14px"></i>
209 209 %if children_groups:
210 210 ${h.literal(' &raquo; '.join(children_groups))}
211 211 %else:
@@ -377,6 +377,30 b''
377 377 </%def>
378 378
379 379
380 ## ARTIFACT RENDERERS
381
382 <%def name="repo_artifact_uid(repo_name, file_uid)">
383 <code><a href="${h.route_path('repo_artifacts_get', repo_name=repo_name, uid=file_uid)}">${file_uid}</a></code>
384 </%def>
385
386 <%def name="repo_artifact_uid_action(repo_name, file_uid)">
387 <i class="tooltip icon-clipboard clipboard-action" data-clipboard-text="${h.route_url('repo_artifacts_get', repo_name=repo_name, uid=file_uid)}" title="${_('Copy the full url')}"></i>
388 </%def>
389
390 <%def name="repo_artifact_actions(repo_name, file_store_id, file_uid)">
391 ## <div class="grid_edit">
392 ## <a href="#Edit" title="${_('Edit')}">${_('Edit')}</a>
393 ## </div>
394 % if h.HasRepoPermissionAny('repository.admin')(c.repo_name):
395 <div class="grid_delete">
396 ${h.secure_form(h.route_path('repo_artifacts_delete', repo_name=repo_name, uid=file_store_id), request=request)}
397 ${h.submit('remove_',_('Delete'),id="remove_artifact_%s" % file_store_id, class_="btn btn-link btn-danger",
398 onclick="return confirm('"+_('Confirm to delete this artifact: %s') % file_uid+"');")}
399 ${h.end_form()}
400 </div>
401 % endif
402 </%def>
403
380 404 <%def name="markup_form(form_id, form_text='', help_text=None)">
381 405
382 406 <div class="markup-form">
@@ -641,7 +641,7 b' File Edit'
641 641 <span class="item">1.2 KiB</span>
642 642 <span class="item last">text/x-python</span>
643 643 <div class="buttons">
644 <a class="btn btn-mini" href="/example/changelog/80ead1899f50a894889e19ffeb49c9cebf5bf045/rhodecode/websetup.py">
644 <a class="btn btn-mini" href="/example/commits/80ead1899f50a894889e19ffeb49c9cebf5bf045/rhodecode/websetup.py">
645 645 <i class="icon-time"></i> history
646 646 </a>
647 647
@@ -425,7 +425,7 b''
425 425 <tr>
426 426 <td>td-active</td>
427 427 <td>Shows active state with icon-true/icon-false.</td>
428 <td class="td-active"><i class="icon-false"></i></td>
428 <td class="td-active"><i class="icon-pr-merge-fail"></i></td>
429 429 </tr>
430 430 <tr>
431 431 <td>td-size</td>
@@ -1,4 +1,11 b''
1 1 <%def name="refs(commit)">
2 ## Build a cache of refs for selector
3 <script>
4 fileTreeRefs = {
5
6 }
7 </script>
8
2 9 %if commit.merge:
3 10 <span class="mergetag tag">
4 11 <i class="icon-merge">${_('merge')}</i>
@@ -10,6 +17,9 b''
10 17 <span class="booktag tag" title="${h.tooltip(_('Bookmark %s') % book)}">
11 18 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=commit.raw_id,_query=dict(at=book))}"><i class="icon-bookmark"></i>${h.shorter(book)}</a>
12 19 </span>
20 <script>
21 fileTreeRefs["${book}"] = {raw_id: "${commit.raw_id}", type:"book", text: "${book}"};
22 </script>
13 23 %endfor
14 24 %endif
15 25
@@ -17,12 +27,18 b''
17 27 <span class="tagtag tag" title="${h.tooltip(_('Tag %s') % tag)}">
18 28 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=commit.raw_id,_query=dict(at=tag))}"><i class="icon-tag"></i>${tag}</a>
19 29 </span>
30 <script>
31 fileTreeRefs["${tag}"] = {raw_id: "${commit.raw_id}", type:"tag", text: "${tag}"};
32 </script>
20 33 %endfor
21 34
22 35 %if commit.branch:
23 36 <span class="branchtag tag" title="${h.tooltip(_('Branch %s') % commit.branch)}">
24 37 <a href="${h.route_path('repo_files:default_path',repo_name=c.repo_name,commit_id=commit.raw_id,_query=dict(at=commit.branch))}"><i class="icon-code-fork"></i>${h.shorter(commit.branch)}</a>
25 38 </span>
39 <script>
40 fileTreeRefs["${commit.branch}"] = {raw_id: "${commit.raw_id}", type:"branch", text: "${commit.branch}"};
41 </script>
26 42 %endif
27 43
28 44 </%def>
@@ -1,42 +1,38 b''
1 1 <%namespace name="base" file="/base/base.mako"/>
2 2
3 <div class="summary-detail-header">
4 <h4 class="item">
5 % if c.file_author:
6 ${_('Last Author')}
7 % else:
8 ${h.literal(_ungettext(u'File Author (%s)',u'File Authors (%s)',len(c.authors)) % ('<b>%s</b>' % len(c.authors))) }
9 % endif
10 </h4>
11 <a href="#" id="show_authors" class="action_link">${_('Show All')}</a>
12 </div>
3 % if c.authors:
4
5 <table class="sidebar-right-content">
6 % for email, user, commits in sorted(c.authors, key=lambda e: c.file_last_commit.author_email!=e[0]):
7 <tr class="file_author tooltip" title="${h.tooltip(h.author_string(email))}">
13 8
14 % if c.authors:
15 <ul class="sidebar-right-content">
16 % for email, user, commits in sorted(c.authors, key=lambda e: c.file_last_commit.author_email!=e[0]):
17 <li class="file_author">
18 <div class="tooltip" title="${h.tooltip(h.author_string(email))}">
19 ${base.gravatar(email, 16)}
20 <div class="user">${h.link_to_user(user)}</div>
21
9 <td>
10 % if not c.file_author:
11 ${base.gravatar(email, 16)}
12 % endif
13 <span class="user commit-author">${h.link_to_user(user)}</span>
22 14 % if c.file_author:
23 <span>- ${h.age_component(c.file_last_commit.date)}</span>
15 <span class="commit-date">- ${h.age_component(c.file_last_commit.date)}</span>
16 <a href="#ShowAuthors" onclick="showAuthors(this, ${("1" if c.annotate else "0")}); return false" class="action_link"> - ${_('Load All Authors')}</a>
24 17 % elif c.file_last_commit.author_email==email:
25 18 <span> (${_('last author')})</span>
26 19 % endif
20 </td>
27 21
22 <td>
28 23 % if not c.file_author:
29 <span>
24 <code>
30 25 % if commits == 1:
31 26 ${commits} ${_('Commit')}
32 27 % else:
33 28 ${commits} ${_('Commits')}
34 29 % endif
35 </span>
30 </code>
36 31 % endif
32 </td>
33 </tr>
37 34
38 </div>
39 </li>
40 35 % endfor
41 </ul>
36 </table>
42 37 % endif
38
This diff has been collapsed as it changes many lines, (551 lines changed) Show them Hide them
@@ -1,9 +1,9 b''
1 1 <%inherit file="/base/base.mako"/>
2 2
3 3 <%def name="title(*args)">
4 ${_('%s Files') % c.repo_name}
4 ${_('{} Files').format(c.repo_name)}
5 5 %if hasattr(c,'file'):
6 &middot; ${h.safe_unicode(c.file.path) or '\\'}
6 &middot; ${(h.safe_unicode(c.file.path) or '\\')}
7 7 %endif
8 8
9 9 %if c.rhodecode_name:
@@ -27,113 +27,321 b''
27 27 </%def>
28 28
29 29 <%def name="main()">
30 <div class="title">
31 ${self.repo_page_title(c.rhodecode_db_repo)}
32 </div>
30 <script type="text/javascript">
31 var fileSourcePage = ${c.file_source_page};
32 var atRef = '${request.GET.get('at', '')}';
33 33
34 <div id="pjax-container" class="summary">
34 // global state for fetching metadata
35 metadataRequest = null;
36
37 // global metadata about URL
38 filesUrlData = ${h.files_url_data(request)|n};
39 </script>
40
41 <div>
35 42 <div id="files_data">
36 43 <%include file='files_pjax.mako'/>
37 44 </div>
38 45 </div>
39 <script>
40 var curState = {
41 commit_id: "${c.commit.raw_id}"
42 };
46
47 <script type="text/javascript">
43 48
44 var getState = function(context) {
45 var url = $(location).attr('href');
46 var _base_url = '${h.route_path("repo_files",repo_name=c.repo_name,commit_id='',f_path='')}';
47 var _annotate_url = '${h.route_path("repo_files:annotated",repo_name=c.repo_name,commit_id='',f_path='')}';
48 _base_url = _base_url.replace('//', '/');
49 _annotate_url = _annotate_url.replace('//', '/');
49 var initFileJS = function () {
50 var state = getFileState();
51
52 // select code link event
53 $("#hlcode").mouseup(getSelectionLink);
50 54
51 //extract f_path from url.
52 var parts = url.split(_base_url);
53 if (parts.length != 2) {
54 parts = url.split(_annotate_url);
55 if (parts.length != 2) {
56 var rev = "tip";
57 var f_path = "";
58 } else {
59 var parts2 = parts[1].split('/');
60 var rev = parts2.shift(); // pop the first element which is the revision
61 var f_path = parts2.join('/');
62 }
55 // file history select2 used for history of file, and switch to
56 var initialCommitData = {
57 at_ref: atRef,
58 id: null,
59 text: '${c.commit.raw_id}',
60 type: 'sha',
61 raw_id: '${c.commit.raw_id}',
62 idx: ${c.commit.idx},
63 files_url: null,
64 };
63 65
64 } else {
65 var parts2 = parts[1].split('/');
66 var rev = parts2.shift(); // pop the first element which is the revision
67 var f_path = parts2.join('/');
66 // check if we have ref info.
67 var selectedRef = fileTreeRefs[atRef];
68 if (selectedRef !== undefined) {
69 $.extend(initialCommitData, selectedRef)
68 70 }
69 71
70 var _node_list_url = pyroutes.url('repo_files_nodelist',
71 {repo_name: templateContext.repo_name,
72 commit_id: rev, f_path: f_path});
73 var _url_base = pyroutes.url('repo_files',
74 {repo_name: templateContext.repo_name,
75 commit_id: rev, f_path:'__FPATH__'});
76 return {
77 url: url,
78 f_path: f_path,
79 rev: rev,
80 commit_id: curState.commit_id,
81 node_list_url: _node_list_url,
82 url_base: _url_base
72 var loadUrl = pyroutes.url('repo_file_history', {'repo_name': templateContext.repo_name, 'commit_id': state.commit_id,'f_path': state.f_path});
73 var cacheKey = '__SINGLE_FILE_REFS__';
74 var cachedDataSource = {};
75
76 var loadRefsData = function (query) {
77 $.ajax({
78 url: loadUrl,
79 data: {},
80 dataType: 'json',
81 type: 'GET',
82 success: function (data) {
83 cachedDataSource[cacheKey] = data;
84 query.callback({results: data.results});
85 }
86 });
87 };
88
89 var feedRefsData = function (query, cachedData) {
90 var data = {results: []};
91 //filter results
92 $.each(cachedData.results, function () {
93 var section = this.text;
94 var children = [];
95 $.each(this.children, function () {
96 if (query.term.length === 0 || this.text.toUpperCase().indexOf(query.term.toUpperCase()) >= 0) {
97 children.push(this)
98 }
99 });
100 data.results.push({
101 'text': section,
102 'children': children
103 })
104 });
105
106 query.callback(data);
83 107 };
108
109 var select2FileHistorySwitcher = function (targetElement, loadUrl, initialData) {
110 var formatResult = function (result, container, query) {
111 return formatSelect2SelectionRefs(result);
112 };
113
114 var formatSelection = function (data, container) {
115 var commit_ref = data;
116
117 var tmpl = '';
118 if (commit_ref.type === 'sha') {
119 tmpl = (commit_ref.raw_id || "").substr(0,8);
120 } else if (commit_ref.type === 'branch') {
121 tmpl = tmpl.concat('<i class="icon-branch"></i> ');
122 tmpl = tmpl.concat(escapeHtml(commit_ref.text));
123 } else if (commit_ref.type === 'tag') {
124 tmpl = tmpl.concat('<i class="icon-tag"></i> ');
125 tmpl = tmpl.concat(escapeHtml(commit_ref.text));
126 } else if (commit_ref.type === 'book') {
127 tmpl = tmpl.concat('<i class="icon-bookmark"></i> ');
128 tmpl = tmpl.concat(escapeHtml(commit_ref.text));
129 }
130 var idx = commit_ref.idx || 0;
131 if (idx !== 0) {
132 tmpl = tmpl.concat('<span class="select-index-number">r{0}</span>'.format(idx));
133 }
134 return tmpl
135 };
136
137 $(targetElement).select2({
138 dropdownAutoWidth: true,
139 width: "resolve",
140 containerCssClass: "drop-menu",
141 dropdownCssClass: "drop-menu-dropdown",
142 query: function(query) {
143 var cachedData = cachedDataSource[cacheKey];
144 if (cachedData) {
145 feedRefsData(query, cachedData)
146 } else {
147 loadRefsData(query)
148 }
149 },
150 initSelection: function(element, callback) {
151 callback(initialData);
152 },
153 formatResult: formatResult,
154 formatSelection: formatSelection
155 });
156
157 };
158
159 select2FileHistorySwitcher('#file_refs_filter', loadUrl, initialCommitData);
160
161 $('#file_refs_filter').on('change', function(e) {
162 var data = $('#file_refs_filter').select2('data');
163 var commit_id = data.id;
164
165 if ("${c.annotate}" === "True") {
166 var url = pyroutes.url('repo_files:annotated',
167 {'repo_name': templateContext.repo_name,
168 'commit_id': commit_id, 'f_path': state.f_path});
169 } else {
170 var url = pyroutes.url('repo_files',
171 {'repo_name': templateContext.repo_name,
172 'commit_id': commit_id, 'f_path': state.f_path});
173 }
174 window.location = url;
175
176 });
177
178 // load file short history
179 $('#file_history_overview').on('click', function(e) {
180 e.preventDefault();
181 path = state.f_path;
182 if (path.indexOf("#") >= 0) {
183 path = path.slice(0, path.indexOf("#"));
184 }
185 var url = pyroutes.url('repo_commits_file',
186 {'repo_name': templateContext.repo_name,
187 'commit_id': state.commit_id, 'f_path': path, 'limit': 6});
188 $('#file_history_container').show();
189 $('#file_history_container').html('<div class="file-history-inner">{0}</div>'.format(_gettext('Loading ...')));
190
191 $.pjax({
192 url: url,
193 container: '#file_history_container',
194 push: false,
195 timeout: 5000
196 });
197 });
198
84 199 };
85 200
86 var metadataRequest = null;
87 var getFilesMetadata = function() {
88 if (metadataRequest && metadataRequest.readyState != 4) {
89 metadataRequest.abort();
90 }
91 if (fileSourcePage) {
92 return false;
201 var initTreeJS = function () {
202 var state = getFileState();
203 getFilesMetadata();
204
205 // fuzzy file filter
206 fileBrowserListeners(state.node_list_url, state.url_base);
207
208 // switch to widget
209 var initialCommitData = {
210 at_ref: atRef,
211 id: null,
212 text: '${c.commit.raw_id}',
213 type: 'sha',
214 raw_id: '${c.commit.raw_id}',
215 idx: ${c.commit.idx},
216 files_url: null,
217 };
218
219 // check if we have ref info.
220 var selectedRef = fileTreeRefs[atRef];
221 if (selectedRef !== undefined) {
222 $.extend(initialCommitData, selectedRef)
93 223 }
94 224
95 if ($('#file-tree-wrapper').hasClass('full-load')) {
96 // in case our HTML wrapper has full-load class we don't
97 // trigger the async load of metadata
98 return false;
99 }
225 var loadUrl = pyroutes.url('repo_refs_data', {'repo_name': templateContext.repo_name});
226 var cacheKey = '__ALL_FILE_REFS__';
227 var cachedDataSource = {};
100 228
101 var state = getState('metadata');
102 var url_data = {
103 'repo_name': templateContext.repo_name,
104 'commit_id': state.commit_id,
105 'f_path': state.f_path
229 var loadRefsData = function (query) {
230 $.ajax({
231 url: loadUrl,
232 data: {},
233 dataType: 'json',
234 type: 'GET',
235 success: function (data) {
236 cachedDataSource[cacheKey] = data;
237 query.callback({results: data.results});
238 }
239 });
106 240 };
107 241
108 var url = pyroutes.url('repo_nodetree_full', url_data);
242 var feedRefsData = function (query, cachedData) {
243 var data = {results: []};
244 //filter results
245 $.each(cachedData.results, function () {
246 var section = this.text;
247 var children = [];
248 $.each(this.children, function () {
249 if (query.term.length === 0 || this.text.toUpperCase().indexOf(query.term.toUpperCase()) >= 0) {
250 children.push(this)
251 }
252 });
253 data.results.push({
254 'text': section,
255 'children': children
256 })
257 });
258
259 //push the typed in commit idx
260 if (!isNaN(query.term)) {
261 var files_url = pyroutes.url('repo_files',
262 {'repo_name': templateContext.repo_name,
263 'commit_id': query.term, 'f_path': state.f_path});
109 264
110 metadataRequest = $.ajax({url: url});
265 data.results.push({
266 'text': _gettext('go to numeric commit'),
267 'children': [{
268 at_ref: null,
269 id: null,
270 text: 'r{0}'.format(query.term),
271 type: 'sha',
272 raw_id: query.term,
273 idx: query.term,
274 files_url: files_url,
275 }]
276 });
277 }
278 query.callback(data);
279 };
280
281 var select2RefFileSwitcher = function (targetElement, loadUrl, initialData) {
282 var formatResult = function (result, container, query) {
283 return formatSelect2SelectionRefs(result);
284 };
285
286 var formatSelection = function (data, container) {
287 var commit_ref = data;
111 288
112 metadataRequest.done(function(data) {
113 $('#file-tree').html(data);
114 timeagoActivate();
289 var tmpl = '';
290 if (commit_ref.type === 'sha') {
291 tmpl = (commit_ref.raw_id || "").substr(0,8);
292 } else if (commit_ref.type === 'branch') {
293 tmpl = tmpl.concat('<i class="icon-branch"></i> ');
294 tmpl = tmpl.concat(escapeHtml(commit_ref.text));
295 } else if (commit_ref.type === 'tag') {
296 tmpl = tmpl.concat('<i class="icon-tag"></i> ');
297 tmpl = tmpl.concat(escapeHtml(commit_ref.text));
298 } else if (commit_ref.type === 'book') {
299 tmpl = tmpl.concat('<i class="icon-bookmark"></i> ');
300 tmpl = tmpl.concat(escapeHtml(commit_ref.text));
301 }
302
303 var idx = commit_ref.idx || 0;
304 if (idx !== 0) {
305 tmpl = tmpl.concat('<span class="select-index-number">r{0}</span>'.format(idx));
306 }
307 return tmpl
308 };
309
310 $(targetElement).select2({
311 dropdownAutoWidth: true,
312 width: "resolve",
313 containerCssClass: "drop-menu",
314 dropdownCssClass: "drop-menu-dropdown",
315 query: function(query) {
316
317 var cachedData = cachedDataSource[cacheKey];
318 if (cachedData) {
319 feedRefsData(query, cachedData)
320 } else {
321 loadRefsData(query)
322 }
323 },
324 initSelection: function(element, callback) {
325 callback(initialData);
326 },
327 formatResult: formatResult,
328 formatSelection: formatSelection
329 });
330
331 };
332
333 select2RefFileSwitcher('#refs_filter', loadUrl, initialCommitData);
334
335 $('#refs_filter').on('change', function(e) {
336 var data = $('#refs_filter').select2('data');
337 window.location = data.files_url
115 338 });
116 metadataRequest.fail(function (data, textStatus, errorThrown) {
117 console.log(data);
118 if (data.status != 0) {
119 alert("Error while fetching metadata.\nError code {0} ({1}).Please consider reloading the page".format(data.status,data.statusText));
120 }
121 });
339
122 340 };
123 341
124 var callbacks = function() {
125 var state = getState('callbacks');
342 $(document).ready(function() {
126 343 timeagoActivate();
127 344
128 // used for history, and switch to
129 var initialCommitData = {
130 id: null,
131 text: '${_("Pick Commit")}',
132 type: 'sha',
133 raw_id: null,
134 files_url: null
135 };
136
137 345 if ($('#trimmed_message_box').height() < 50) {
138 346 $('#message_expand').hide();
139 347 }
@@ -144,181 +352,18 b''
144 352 });
145 353
146 354 if (fileSourcePage) {
147 // variants for with source code, not tree view
148
149 // select code link event
150 $("#hlcode").mouseup(getSelectionLink);
151
152 // file history select2
153 select2FileHistorySwitcher('#diff1', initialCommitData, state);
154
155 // show at, diff to actions handlers
156 $('#diff1').on('change', function(e) {
157 $('#diff_to_commit').removeClass('disabled').removeAttr("disabled");
158 $('#diff_to_commit').val(_gettext('Diff to Commit ') + e.val.truncateAfter(8, '...'));
159
160 $('#show_at_commit').removeClass('disabled').removeAttr("disabled");
161 $('#show_at_commit').val(_gettext('Show at Commit ') + e.val.truncateAfter(8, '...'));
162 });
163
164 $('#diff_to_commit').on('click', function(e) {
165 var diff1 = $('#diff1').val();
166 var diff2 = $('#diff2').val();
167
168 var url_data = {
169 repo_name: templateContext.repo_name,
170 source_ref: diff1,
171 source_ref_type: 'rev',
172 target_ref: diff2,
173 target_ref_type: 'rev',
174 merge: 1,
175 f_path: state.f_path
176 };
177 window.location = pyroutes.url('repo_compare', url_data);
178 });
179
180 $('#show_at_commit').on('click', function(e) {
181 var diff1 = $('#diff1').val();
182
183 var annotate = $('#annotate').val();
184 if (annotate === "True") {
185 var url = pyroutes.url('repo_files:annotated',
186 {'repo_name': templateContext.repo_name,
187 'commit_id': diff1, 'f_path': state.f_path});
188 } else {
189 var url = pyroutes.url('repo_files',
190 {'repo_name': templateContext.repo_name,
191 'commit_id': diff1, 'f_path': state.f_path});
192 }
193 window.location = url;
194
195 });
196
197 // show more authors
198 $('#show_authors').on('click', function(e) {
199 e.preventDefault();
200 var url = pyroutes.url('repo_file_authors',
201 {'repo_name': templateContext.repo_name,
202 'commit_id': state.rev, 'f_path': state.f_path});
203
204 $.pjax({
205 url: url,
206 data: 'annotate=${"1" if c.annotate else "0"}',
207 container: '#file_authors',
208 push: false,
209 timeout: pjaxTimeout
210 }).complete(function(){
211 $('#show_authors').hide();
212 })
213 });
214
215 // load file short history
216 $('#file_history_overview').on('click', function(e) {
217 e.preventDefault();
218 path = state.f_path;
219 if (path.indexOf("#") >= 0) {
220 path = path.slice(0, path.indexOf("#"));
221 }
222 var url = pyroutes.url('repo_changelog_file',
223 {'repo_name': templateContext.repo_name,
224 'commit_id': state.rev, 'f_path': path, 'limit': 6});
225 $('#file_history_container').show();
226 $('#file_history_container').html('<div class="file-history-inner">{0}</div>'.format(_gettext('Loading ...')));
227
228 $.pjax({
229 url: url,
230 container: '#file_history_container',
231 push: false,
232 timeout: pjaxTimeout
233 })
234 });
235
236 }
237 else {
238 getFilesMetadata();
239
240 // fuzzy file filter
241 fileBrowserListeners(state.node_list_url, state.url_base);
242
243 // switch to widget
244 select2RefSwitcher('#refs_filter', initialCommitData);
245 $('#refs_filter').on('change', function(e) {
246 var data = $('#refs_filter').select2('data');
247 curState.commit_id = data.raw_id;
248 $.pjax({url: data.files_url, container: '#pjax-container', timeout: pjaxTimeout});
249 });
250
251 $("#prev_commit_link").on('click', function(e) {
252 var data = $(this).data();
253 curState.commit_id = data.commitId;
254 });
255
256 $("#next_commit_link").on('click', function(e) {
257 var data = $(this).data();
258 curState.commit_id = data.commitId;
259 });
260
261 $('#at_rev').on("keypress", function(e) {
262 /* ENTER PRESSED */
263 if (e.keyCode === 13) {
264 var rev = $('#at_rev').val();
265 // explicit reload page here. with pjax entering bad input
266 // produces not so nice results
267 window.location = pyroutes.url('repo_files',
268 {'repo_name': templateContext.repo_name,
269 'commit_id': rev, 'f_path': state.f_path});
270 }
271 });
272 }
273 };
274
275 var pjaxTimeout = 5000;
276
277 $(document).pjax(".pjax-link", "#pjax-container", {
278 "fragment": "#pjax-content",
279 "maxCacheLength": 1000,
280 "timeout": pjaxTimeout
281 });
282
283 // define global back/forward states
284 var isPjaxPopState = false;
285 $(document).on('pjax:popstate', function() {
286 isPjaxPopState = true;
287 });
288
289 $(document).on('pjax:end', function(xhr, options) {
290 if (isPjaxPopState) {
291 isPjaxPopState = false;
292 callbacks();
293 _NODEFILTER.resetFilter();
355 initFileJS()
356 } else {
357 initTreeJS()
294 358 }
295 359
296 // run callback for tracking if defined for google analytics etc.
297 // this is used to trigger tracking on pjax
298 if (typeof window.rhodecode_statechange_callback !== 'undefined') {
299 var state = getState('statechange');
300 rhodecode_statechange_callback(state.url, null)
301 }
302 });
303
304 $(document).on('pjax:success', function(event, xhr, options) {
305 if (event.target.id == "file_history_container") {
306 $('#file_history_overview').hide();
307 $('#file_history_overview_full').show();
308 timeagoActivate();
309 } else {
310 callbacks();
311 }
312 });
313
314 $(document).ready(function() {
315 callbacks();
316 360 var search_GET = "${request.GET.get('search','')}";
317 361 if (search_GET === "1") {
318 _NODEFILTER.initFilter();
362 NodeFilter.initFilter();
363 NodeFilter.focus();
319 364 }
320 365 });
321 366
322 367 </script>
323 368
324 </%def>
369 </%def> No newline at end of file
@@ -1,7 +1,7 b''
1 1 <%inherit file="/base/base.mako"/>
2 2
3 3 <%def name="title()">
4 ${_('%s Files Add') % c.repo_name}
4 ${_('{} Files Add').format(c.repo_name)}
5 5 %if c.rhodecode_name:
6 6 &middot; ${h.branding(c.rhodecode_name)}
7 7 %endif
@@ -11,79 +11,64 b''
11 11 ${self.menu_items(active='repositories')}
12 12 </%def>
13 13
14 <%def name="breadcrumbs_links()">
15 ${_('Add new file')} @ ${h.show_id(c.commit)} ${_('Branch')}: ${c.commit.branch}
16 </%def>
14 <%def name="breadcrumbs_links()"></%def>
17 15
18 16 <%def name="menu_bar_subnav()">
19 17 ${self.repo_menu(active='files')}
20 18 </%def>
21 19
22 20 <%def name="main()">
21
23 22 <div class="box">
24 <div class="title">
25 ${self.repo_page_title(c.rhodecode_db_repo)}
23
24 <div class="edit-file-title">
25 <span class="title-heading">${_('Add new file')} @ <code>${h.show_id(c.commit)}</code></span>
26 % if c.commit.branch:
27 <span class="tag branchtag">
28 <i class="icon-branch"></i> ${c.commit.branch}
29 </span>
30 % endif
26 31 </div>
27 <div class="edit-file-title">
28 ${self.breadcrumbs()}
29 </div>
30 ${h.secure_form(h.route_path('repo_files_create_file', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path), id='eform', enctype="multipart/form-data", class_="form-horizontal", request=request)}
32
33 ${h.secure_form(h.route_path('repo_files_create_file', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path), id='eform', request=request)}
31 34 <div class="edit-file-fieldset">
32 <div class="fieldset">
33 <div id="destination-label" class="left-label">
34 ${_('Path')}:
35 </div>
36 <div class="right-content">
37 <div id="specify-custom-path-container">
38 <span id="path-breadcrumbs">${h.files_breadcrumbs(c.repo_name,c.commit.raw_id,c.f_path)}</span>
39 <a class="custom-path-link" id="specify-custom-path" href="#">${_('Specify Custom Path')}</a>
35 <div class="path-items">
36 <ul>
37 <li class="breadcrumb-path">
38 <div>
39 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path='')}"><i class="icon-home"></i></a> /
40 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path)}">${c.f_path}</a> ${('/' if c.f_path else '')}
40 41 </div>
41 <div id="remove-custom-path-container" style="display: none;">
42 ${c.repo_name}/
43 <input type="input-small" value="${c.f_path}" size="46" name="location" id="location">
44 <a class="custom-path-link" id="remove-custom-path" href="#">${_('Remove Custom Path')}</a>
45 </div>
46 </div>
42 </li>
43 <li class="location-path">
44 <input class="file-name-input input-small" type="text" value="" name="filename" id="filename" placeholder="${_('Filename e.g example.py, or docs/readme.md')}">
45 </li>
46 </ul>
47 47 </div>
48 <div id="filename_container" class="fieldset">
49 <div class="filename-label left-label">
50 ${_('Filename')}:
51 </div>
52 <div class="right-content">
53 <input class="input-small" type="text" value="" size="46" name="filename" id="filename">
54 <p>${_('or')} <a id="upload_file_enable" href="#">${_('Upload File')}</a></p>
55 </div>
56 </div>
57 <div id="upload_file_container" class="fieldset" style="display: none;">
58 <div class="filename-label left-label">
59 ${_('Filename')}:
60 </div>
61 <div class="right-content">
62 <input class="input-small" type="text" value="" size="46" name="filename_upload" id="filename_upload" placeholder="${_('No file selected')}">
63 </div>
64 <div class="filename-label left-label file-upload-label">
65 ${_('Upload file')}:
66 </div>
67 <div class="right-content file-upload-input">
68 <label for="upload_file" class="btn btn-default">Browse</label>
69 48
70 <input type="file" name="upload_file" id="upload_file">
71 <p>${_('or')} <a id="file_enable" href="#">${_('Create New File')}</a></p>
72 </div>
73 </div>
74 49 </div>
50
75 51 <div class="table">
76 52 <div id="files_data">
53
77 54 <div id="codeblock" class="codeblock">
78 <div class="code-header form" id="set_mode_header">
79 <div class="fields">
80 ${h.dropdownmenu('set_mode','plain',[('plain',_('plain'))],enable_filter=True)}
81 <label for="line_wrap">${_('line wraps')}</label>
82 ${h.dropdownmenu('line_wrap', 'off', [('on', _('on')), ('off', _('off')),])}
55 <div class="editor-items">
56 <div class="editor-action active show-editor pull-left" onclick="fileEditor.showEditor(); return false">
57 ${_('Edit')}
58 </div>
59
60 <div class="editor-action show-preview pull-left" onclick="fileEditor.showPreview(); return false">
61 ${_('Preview')}
62 </div>
83 63
84 <div id="render_preview" class="btn btn-small preview hidden" >${_('Preview')}</div>
64 <div class="pull-right">
65 ${h.dropdownmenu('line_wrap', 'off', [('on', _('Line wraps on')), ('off', _('line wraps off'))], extra_classes=['last-item'])}
66 </div>
67 <div class="pull-right">
68 ${h.dropdownmenu('set_mode','plain',[('plain', _('plain'))], enable_filter=True)}
69 </div>
85 70 </div>
86 </div>
71
87 72 <div id="editor_container">
88 73 <pre id="editor_pre"></pre>
89 74 <textarea id="editor" name="content" ></textarea>
@@ -95,144 +80,35 b''
95 80
96 81 <div class="edit-file-fieldset">
97 82 <div class="fieldset">
98 <div id="commit-message-label" class="commit-message-label left-label">
99 ${_('Commit Message')}:
100 </div>
101 <div class="right-content">
102 <div class="message">
103 <textarea id="commit" name="message" placeholder="${c.default_message}"></textarea>
104 </div>
83 <div class="message">
84 <textarea id="commit" name="message" placeholder="${c.default_message}"></textarea>
105 85 </div>
106 86 </div>
107 <div class="pull-right">
108 ${h.reset('reset',_('Cancel'),class_="btn btn-small")}
109 ${h.submit('commit_btn',_('Commit changes'),class_="btn btn-small btn-success")}
87 <div class="pull-left">
88 ${h.submit('commit_btn',_('Commit changes'), class_="btn btn-small btn-success")}
110 89 </div>
111 90 </div>
112 91 ${h.end_form()}
113 92 </div>
93
114 94 <script type="text/javascript">
115 95
116 $('#commit_btn').on('click', function() {
117 var button = $(this);
118 if (button.hasClass('clicked')) {
119 button.attr('disabled', true);
120 } else {
121 button.addClass('clicked');
122 }
123 });
124
125 $('#specify-custom-path').on('click', function(e){
126 e.preventDefault();
127 $('#specify-custom-path-container').hide();
128 $('#remove-custom-path-container').show();
129 $('#destination-label').css('margin-top', '13px');
130 });
131
132 $('#remove-custom-path').on('click', function(e){
133 e.preventDefault();
134 $('#specify-custom-path-container').show();
135 $('#remove-custom-path-container').hide();
136 $('#location').val('${c.f_path}');
137 $('#destination-label').css('margin-top', '0');
138 });
96 $(document).ready(function () {
97 var modes_select = $('#set_mode');
98 var filename_selector = '#filename';
99 fillCodeMirrorOptions(modes_select);
139 100
140 var hide_upload = function(){
141 $('#files_data').show();
142 $('#upload_file_container').hide();
143 $('#filename_container').show();
144 };
145
146 $('#file_enable').on('click', function(e){
147 e.preventDefault();
148 hide_upload();
149 });
150
151 $('#upload_file_enable').on('click', function(e){
152 e.preventDefault();
153 $('#files_data').hide();
154 $('#upload_file_container').show();
155 $('#filename_container').hide();
156 if (detectIE() && detectIE() <= 9) {
157 $('#upload_file_container .file-upload-input label').hide();
158 $('#upload_file_container .file-upload-input span').hide();
159 $('#upload_file_container .file-upload-input input').show();
160 }
161 });
162
163 $('#upload_file').on('change', function() {
164 if (this.files && this.files[0]) {
165 $('#filename_upload').val(this.files[0].name);
166 }
167 });
168
169 hide_upload();
170
171 var renderer = "";
172 var reset_url = "${h.route_path('repo_files',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path)}";
173 var myCodeMirror = initCodeMirror('editor', reset_url, false);
101 fileEditor = new FileEditor('#editor');
174 102
175 var modes_select = $('#set_mode');
176 fillCodeMirrorOptions(modes_select);
177
178 var filename_selector = '#filename';
179 var callback = function(filename, mimetype, mode){
180 CodeMirrorPreviewEnable(mode);
181 };
182 // on change of select field set mode
183 setCodeMirrorModeFromSelect(
184 modes_select, filename_selector, myCodeMirror, callback);
185
186 // on entering the new filename set mode, from given extension
187 setCodeMirrorModeFromInput(
188 modes_select, filename_selector, myCodeMirror, callback);
189
190 // if the file is renderable set line wraps automatically
191 if (renderer !== ""){
192 var line_wrap = 'on';
193 $($('#line_wrap option[value="'+line_wrap+'"]')[0]).attr("selected", "selected");
194 setCodeMirrorLineWrap(myCodeMirror, true);
195 }
196
197 // on select line wraps change the editor
198 $('#line_wrap').on('change', function(e){
199 var selected = e.currentTarget;
200 var line_wraps = {'on': true, 'off': false}[selected.value];
201 setCodeMirrorLineWrap(myCodeMirror, line_wraps)
202 });
103 // on change of select field set mode
104 setCodeMirrorModeFromSelect(modes_select, filename_selector, fileEditor.cm, null);
203 105
204 // render preview/edit button
205 $('#render_preview').on('click', function(e){
206 if($(this).hasClass('preview')){
207 $(this).removeClass('preview');
208 $(this).html("${_('Edit')}");
209 $('#editor_preview').show();
210 $(myCodeMirror.getWrapperElement()).hide();
106 // on entering the new filename set mode, from given extension
107 setCodeMirrorModeFromInput(modes_select, filename_selector, fileEditor.cm, null);
211 108
212 var possible_renderer = {
213 'rst':'rst',
214 'markdown':'markdown',
215 'gfm': 'markdown'}[myCodeMirror.getMode().name];
216 var _text = myCodeMirror.getValue();
217 var _renderer = possible_renderer || DEFAULT_RENDERER;
218 var post_data = {'text': _text, 'renderer': _renderer, 'csrf_token': CSRF_TOKEN};
219 $('#editor_preview').html(_gettext('Loading ...'));
220 var url = pyroutes.url('repo_commit_comment_preview',
221 {'repo_name': '${c.repo_name}',
222 'commit_id': '${c.commit.raw_id}'});
109 $('#filename').focus();
223 110
224 ajaxPOST(url, post_data, function(o){
225 $('#editor_preview').html(o);
226 })
227 }
228 else{
229 $(this).addClass('preview');
230 $(this).html("${_('Preview')}");
231 $('#editor_preview').hide();
232 $(myCodeMirror.getWrapperElement()).show();
233 }
234 111 });
235 $('#filename').focus();
236 112
237 113 </script>
238 114 </%def>
@@ -2,53 +2,60 b''
2 2 <div id="codeblock" class="browserblock">
3 3 <div class="browser-header">
4 4 <div class="browser-nav">
5 ${h.form(h.current_route_path(request), method='GET', id='at_rev_form')}
5
6 6 <div class="info_box">
7 ${h.hidden('refs_filter')}
7
8 8 <div class="info_box_elem previous">
9 <a id="prev_commit_link" data-commit-id="${c.prev_commit.raw_id}" class="pjax-link ${'disabled' if c.url_prev == '#' else ''}" href="${c.url_prev}" title="${_('Previous commit')}"><i class="icon-left"></i></a>
9 <a id="prev_commit_link" data-commit-id="${c.prev_commit.raw_id}" class=" ${('disabled' if c.url_prev == '#' else '')}" href="${c.url_prev}" title="${_('Previous commit')}"><i class="icon-left"></i></a>
10 10 </div>
11 <div class="info_box_elem">${h.text('at_rev',value=c.commit.idx)}</div>
11
12 ${h.hidden('refs_filter')}
13
12 14 <div class="info_box_elem next">
13 <a id="next_commit_link" data-commit-id="${c.next_commit.raw_id}" class="pjax-link ${'disabled' if c.url_next == '#' else ''}" href="${c.url_next}" title="${_('Next commit')}"><i class="icon-right"></i></a>
15 <a id="next_commit_link" data-commit-id="${c.next_commit.raw_id}" class=" ${('disabled' if c.url_next == '#' else '')}" href="${c.url_next}" title="${_('Next commit')}"><i class="icon-right"></i></a>
14 16 </div>
15 17 </div>
16 ${h.end_form()}
17 18
18 <div id="search_activate_id" class="search_activate">
19 <a class="btn btn-default" id="filter_activate" href="javascript:void(0)">${_('Search File List')}</a>
20 </div>
21 <div id="search_deactivate_id" class="search_activate hidden">
22 <a class="btn btn-default" id="filter_deactivate" href="javascript:void(0)">${_('Close File List')}</a>
23 </div>
24 19 % if h.HasRepoPermissionAny('repository.write','repository.admin')(c.repo_name):
25 <div title="${_('Add New File')}" class="btn btn-primary new-file">
26 <a href="${h.route_path('repo_files_add_file',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path, _anchor='edit')}">
27 ${_('Add File')}</a>
28 </div>
29 % endif
30 % if c.enable_downloads:
31 <% at_path = '{}.zip'.format(request.GET.get('at') or c.commit.raw_id[:6]) %>
32 <div title="${_('Download tree at {}').format(at_path)}" class="btn btn-default new-file">
33 <a href="${h.route_path('repo_archivefile',repo_name=c.repo_name, fname='{}.zip'.format(c.commit.raw_id))}">
34 ${_('Download tree at {}').format(at_path)}
20 <div>
21 <a class="btn btn-primary new-file" href="${h.route_path('repo_files_upload_file',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path)}">
22 ${_('Upload File')}
23 </a>
24 <a class="btn btn-primary new-file" href="${h.route_path('repo_files_add_file',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path)}">
25 ${_('Add File')}
35 26 </a>
36 27 </div>
37 28 % endif
29
30 % if c.enable_downloads:
31 <% at_path = '{}'.format(request.GET.get('at') or c.commit.raw_id[:6]) %>
32 <div class="btn btn-default new-file">
33 % if c.f_path == '/':
34 <a href="${h.route_path('repo_archivefile',repo_name=c.repo_name, fname='{}.zip'.format(c.commit.raw_id))}">
35 ${_('Download full tree ZIP')}
36 </a>
37 % else:
38 <a href="${h.route_path('repo_archivefile',repo_name=c.repo_name, fname='{}.zip'.format(c.commit.raw_id), _query={'at_path':c.f_path})}">
39 ${_('Download this tree ZIP')}
40 </a>
41 % endif
42 </div>
43 % endif
44
45 <div class="files-quick-filter">
46 <ul class="files-filter-box">
47 <li class="files-filter-box-path">
48 <i class="icon-search"></i>
49 </li>
50 <li class="files-filter-box-input">
51 <input onkeydown="NodeFilter.initFilter(event)" class="init" type="text" placeholder="Quick filter" name="filter" size="25" id="node_filter" autocomplete="off">
52 </li>
53 </ul>
54 </div>
38 55 </div>
39 56
40 <div class="browser-search">
41 <div class="node-filter">
42 <div class="node_filter_box hidden" id="node_filter_box_loading" >${_('Loading file list...')}</div>
43 <div class="node_filter_box hidden" id="node_filter_box" >
44 <div class="node-filter-path">${h.get_last_path_part(c.file)}/</div>
45 <div class="node-filter-input">
46 <input class="init" type="text" name="filter" size="25" id="node_filter" autocomplete="off">
47 </div>
48 </div>
49 </div>
50 </div>
51 57 </div>
58
52 59 ## file tree is computed from caches, and filled in
53 60 <div id="file-tree">
54 61 ${c.file_tree |n}
@@ -1,5 +1,11 b''
1 <div id="file-tree-wrapper" class="browser-body ${'full-load' if c.full_load else ''}">
2 <table class="code-browser rctable">
1 <%
2 if request.GET.get('at'):
3 query={'at': request.GET.get('at')}
4 else:
5 query=None
6 %>
7 <div id="file-tree-wrapper" class="browser-body ${('full-load' if c.full_load else '')}">
8 <table class="code-browser rctable repo_summary">
3 9 <thead>
4 10 <tr>
5 11 <th>${_('Name')}</th>
@@ -11,19 +17,13 b''
11 17 </thead>
12 18
13 19 <tbody id="tbody">
14 %if c.file.parent:
15 <tr class="parity0">
16 <td class="td-componentname">
17 <a href="${h.route_path('repo_files',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.file.parent.path)}" class="pjax-link">
18 <i class="icon-directory"></i>..
19 </a>
20 <tr>
21 <td colspan="5">
22
23 ${h.files_breadcrumbs(c.repo_name,c.commit.raw_id,c.file.path, request.GET.get('at'), limit_items=True)}
24
20 25 </td>
21 <td></td>
22 <td></td>
23 <td></td>
24 <td></td>
25 </tr>
26 %endif
26 </tr>
27 27 %for cnt,node in enumerate(c.file):
28 28 <tr class="parity${cnt%2}">
29 29 <td class="td-componentname">
@@ -38,8 +38,9 b''
38 38 % endif
39 39 </span>
40 40 % else:
41 <a href="${h.route_path('repo_files',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=h.safe_unicode(node.path))}" class="pjax-link">
42 <i class="${'icon-file-text browser-file' if node.is_file() else 'icon-directory browser-dir'}"></i>${node.name}
41
42 <a href="${h.route_path('repo_files',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=h.safe_unicode(node.path), _query=query)}">
43 <i class="${('icon-file-text browser-file' if node.is_file() else 'icon-directory browser-dir')}"></i>${node.name}
43 44 </a>
44 45 % endif
45 46 </td>
@@ -1,7 +1,7 b''
1 1 <%inherit file="/base/base.mako"/>
2 2
3 3 <%def name="title()">
4 ${_('%s Files Delete') % c.repo_name}
4 ${_('{} Files Delete').format(c.repo_name)}
5 5 %if c.rhodecode_name:
6 6 &middot; ${h.branding(c.rhodecode_name)}
7 7 %endif
@@ -11,32 +11,40 b''
11 11 ${self.menu_items(active='repositories')}
12 12 </%def>
13 13
14 <%def name="breadcrumbs_links()">
15 ${_('Delete file')} @ ${h.show_id(c.commit)}
16 </%def>
14 <%def name="breadcrumbs_links()"></%def>
17 15
18 16 <%def name="menu_bar_subnav()">
19 17 ${self.repo_menu(active='files')}
20 18 </%def>
21 19
22 20 <%def name="main()">
21
23 22 <div class="box">
24 <div class="title">
25 ${self.repo_page_title(c.rhodecode_db_repo)}
23
24 <div class="edit-file-title">
25 <span class="title-heading">${_('Delete file')} @ <code>${h.show_id(c.commit)}</code></span>
26 % if c.commit.branch:
27 <span class="tag branchtag">
28 <i class="icon-branch"></i> ${c.commit.branch}
29 </span>
30 % endif
26 31 </div>
27 <div class="edit-file-title">
28 ${self.breadcrumbs()}
29 </div>
30 ${h.secure_form(h.route_path('repo_files_delete_file', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path), id='eform', class_="form-horizontal", request=request)}
32
33 ${h.secure_form(h.route_path('repo_files_delete_file', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path), id='eform', request=request)}
31 34 <div class="edit-file-fieldset">
32 <div class="fieldset">
33 <div id="destination-label" class="left-label">
34 ${_('Path')}:
35 </div>
36 <div class="right-content">
37 <span id="path-breadcrumbs">${h.files_breadcrumbs(c.repo_name,c.commit.raw_id,c.f_path)}</span>
38 </div>
35 <div class="path-items">
36 <li class="breadcrumb-path">
37 <div>
38 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path='')}"><i class="icon-home"></i></a> /
39 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.file.dir_path)}">${c.file.dir_path}</a> ${('/' if c.file.dir_path else '')}
40 </div>
41 </li>
42 <li class="location-path">
43 <input type="hidden" value="${c.f_path}" name="root_path">
44 <input class="file-name-input input-small" type="text" value="${c.file.name}" name="filename" id="filename" disabled="disabled">
45 </li>
39 46 </div>
47
40 48 </div>
41 49
42 50 <div id="codeblock" class="codeblock delete-file-preview">
@@ -56,20 +64,26 b''
56 64
57 65 <div class="edit-file-fieldset">
58 66 <div class="fieldset">
59 <div id="commit-message-label" class="commit-message-label left-label">
60 ${_('Commit Message')}:
61 </div>
62 <div class="right-content">
63 <div class="message">
64 <textarea id="commit" name="message" placeholder="${c.default_message}"></textarea>
65 </div>
67 <div class="message">
68 <textarea id="commit" name="message" placeholder="${c.default_message}"></textarea>
66 69 </div>
67 70 </div>
68 <div class="pull-right">
69 ${h.reset('reset',_('Cancel'),class_="btn btn-small btn-danger")}
70 ${h.submit('commit',_('Delete File'),class_="btn btn-small btn-danger-action")}
71 <div class="pull-left">
72 ${h.submit('commit',_('Commit changes'),class_="btn btn-small btn-danger-action")}
71 73 </div>
72 74 </div>
73 75 ${h.end_form()}
74 76 </div>
77
78
79 <script type="text/javascript">
80
81 $(document).ready(function () {
82
83 fileEditor = new FileEditor('#editor');
84
85 });
86
87 </script>
88
75 89 </%def>
@@ -1,7 +1,7 b''
1 1 <%inherit file="/base/base.mako"/>
2 2
3 3 <%def name="title()">
4 ${_('%s File Edit') % c.repo_name}
4 ${_('{} Files Edit').format(c.repo_name)}
5 5 %if c.rhodecode_name:
6 6 &middot; ${h.branding(c.rhodecode_name)}
7 7 %endif
@@ -11,187 +11,114 b''
11 11 ${self.menu_items(active='repositories')}
12 12 </%def>
13 13
14 <%def name="breadcrumbs_links()">
15 ${_('Edit file')} @ ${h.show_id(c.commit)}
16 </%def>
14 <%def name="breadcrumbs_links()"></%def>
17 15
18 16 <%def name="menu_bar_subnav()">
19 17 ${self.repo_menu(active='files')}
20 18 </%def>
21 19
22 20 <%def name="main()">
23 <% renderer = h.renderer_from_filename(c.f_path)%>
21
24 22 <div class="box">
25 <div class="title">
26 ${self.repo_page_title(c.rhodecode_db_repo)}
23
24 <div class="edit-file-title">
25 <span class="title-heading">${_('Edit file')} @ <code>${h.show_id(c.commit)}</code></span>
26 % if c.commit.branch:
27 <span class="tag branchtag">
28 <i class="icon-branch"></i> ${c.commit.branch}
29 </span>
30 % endif
27 31 </div>
28 <div class="edit-file-title">
29 ${self.breadcrumbs()}
30 </div>
32
33 ${h.secure_form(h.route_path('repo_files_update_file', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path), id='eform', request=request)}
31 34 <div class="edit-file-fieldset">
32 <div class="fieldset">
33 <div id="destination-label" class="left-label">
34 ${_('Path')}:
35 </div>
36 <div class="right-content">
37 <div id="specify-custom-path-container">
38 <span id="path-breadcrumbs">${h.files_breadcrumbs(c.repo_name,c.commit.raw_id,c.f_path)}</span>
35 <div class="path-items">
36 <ul>
37 <li class="breadcrumb-path">
38 <div>
39 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path='')}"><i class="icon-home"></i></a> /
40 <a href="${h.route_path('repo_files', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.file.dir_path)}">${c.file.dir_path}</a> ${('/' if c.file.dir_path else '')}
39 41 </div>
40 </div>
42 </li>
43 <li class="location-path">
44 <input type="hidden" value="${c.f_path}" name="root_path">
45 <input class="file-name-input input-small" type="text" value="${c.file.name}" name="filename" id="filename" placeholder="${_('Filename e.g example.py, or docs/readme.md')}">
46 </li>
47 </ul>
41 48 </div>
49
42 50 </div>
43 51
44 52 <div class="table">
45 ${h.secure_form(h.route_path('repo_files_update_file', repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path), id='eform', request=request)}
46 <div id="codeblock" class="codeblock" >
47 <div class="code-header">
48 <div class="stats">
49 <i class="icon-file"></i>
50 <span class="item">${h.link_to("r%s:%s" % (c.file.commit.idx,h.short_id(c.file.commit.raw_id)),h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.file.commit.raw_id))}</span>
51 <span class="item">${h.format_byte_size_binary(c.file.size)}</span>
52 <span class="item last">${c.file.mimetype}</span>
53 <div class="buttons">
54 <a class="btn btn-mini" href="${h.route_path('repo_changelog_file',repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path)}">
55 <i class="icon-time"></i> ${_('history')}
56 </a>
53 <div id="files_data">
57 54
58 % if h.HasRepoPermissionAny('repository.write','repository.admin')(c.repo_name):
59 % if not c.file.is_binary:
60 %if True:
61 ${h.link_to(_('source'), h.route_path('repo_files', repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path),class_="btn btn-mini")}
62 %else:
63 ${h.link_to(_('annotation'),h.route_path('repo_files:annotated',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path),class_="btn btn-mini")}
64 %endif
55 <div id="codeblock" class="codeblock">
56 <div class="editor-items">
57 <div class="editor-action active show-editor pull-left" onclick="fileEditor.showEditor(); return false">
58 ${_('Edit')}
59 </div>
60
61 <div class="editor-action show-preview pull-left" onclick="fileEditor.showPreview(); return false">
62 ${_('Preview')}
63 </div>
65 64
66 <a class="btn btn-mini" href="${h.route_path('repo_file_raw',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path)}">
67 ${_('raw')}
68 </a>
69 <a class="btn btn-mini" href="${h.route_path('repo_file_download',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path)}">
70 <i class="icon-archive"></i> ${_('download')}
71 </a>
72 % endif
73 % endif
65 <div class="pull-right">
66 ${h.dropdownmenu('line_wrap', 'off', [('on', _('Line wraps on')), ('off', _('line wraps off')),])}
67 </div>
68 <div class="pull-right">
69 ${h.dropdownmenu('set_mode','plain',[('plain', _('plain'))],enable_filter=True)}
70 </div>
74 71 </div>
75 </div>
76 <div class="form">
77 <label for="set_mode">${_('Editing file')}:</label>
78 ${'%s /' % c.file.dir_path if c.file.dir_path else c.file.dir_path}
79 <input id="filename" type="text" name="filename" value="${c.file.name}">
80 72
81 ${h.dropdownmenu('set_mode','plain',[('plain',_('plain'))],enable_filter=True)}
82 <label for="line_wrap">${_('line wraps')}</label>
83 ${h.dropdownmenu('line_wrap', 'off', [('on', _('on')), ('off', _('off')),])}
84
85 <div id="render_preview" class="btn btn-small preview hidden">${_('Preview')}</div>
86 </div>
87 </div>
88 <div id="editor_container">
89 <pre id="editor_pre"></pre>
90 <textarea id="editor" name="content" >${h.escape(c.file.content)|n}</textarea>
91 <div id="editor_preview" ></div>
73 <div id="editor_container">
74 <pre id="editor_pre"></pre>
75 <textarea id="editor" name="content" >${h.escape(c.file.content)|n}</textarea>
76 <div id="editor_preview" ></div>
77 </div>
92 78 </div>
93 79 </div>
94 80 </div>
95 81
96 82 <div class="edit-file-fieldset">
97 83 <div class="fieldset">
98 <div id="commit-message-label" class="commit-message-label left-label">
99 ${_('Commit Message')}:
100 </div>
101 <div class="right-content">
102 <div class="message">
103 <textarea id="commit" name="message" placeholder="${c.default_message}"></textarea>
104 </div>
84 <div class="message">
85 <textarea id="commit" name="message" placeholder="${c.default_message}"></textarea>
105 86 </div>
106 87 </div>
107 <div class="pull-right">
108 ${h.reset('reset',_('Cancel'),class_="btn btn-small")}
109 ${h.submit('commit',_('Commit changes'),class_="btn btn-small btn-success")}
88 <div class="pull-left">
89 ${h.submit('commit_btn',_('Commit changes'), class_="btn btn-small btn-success")}
110 90 </div>
111 91 </div>
112 92 ${h.end_form()}
113 93 </div>
114 94
115 95 <script type="text/javascript">
116 $(document).ready(function(){
117 var renderer = "${renderer}";
118 var reset_url = "${h.route_path('repo_files',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.file.path)}";
119 var myCodeMirror = initCodeMirror('editor', reset_url);
120 96
97 $(document).ready(function() {
121 98 var modes_select = $('#set_mode');
99 var filename_selector = '#filename';
122 100 fillCodeMirrorOptions(modes_select);
123 101
102 fileEditor = new FileEditor('#editor');
103
124 104 // try to detect the mode based on the file we edit
125 var mimetype = "${c.file.mimetype}";
126 var detected_mode = detectCodeMirrorMode(
127 "${c.file.name}", mimetype);
105 var detected_mode = detectCodeMirrorMode("${c.file.name}", "${c.file.mimetype}");
128 106
129 if(detected_mode){
130 setCodeMirrorMode(myCodeMirror, detected_mode);
131 $(modes_select).select2("val", mimetype);
132 $(modes_select).change();
133 setCodeMirrorMode(myCodeMirror, detected_mode);
107 if (detected_mode) {
108 setCodeMirrorMode(fileEditor.cm, detected_mode);
109
110 var mimetype = $(modes_select).find("option[mode={0}]".format(detected_mode)).val();
111 $(modes_select).select2("val", mimetype).trigger('change');
134 112 }
135 113
136 var filename_selector = '#filename';
137 var callback = function(filename, mimetype, mode){
138 CodeMirrorPreviewEnable(mode);
139 };
140 114 // on change of select field set mode
141 setCodeMirrorModeFromSelect(
142 modes_select, filename_selector, myCodeMirror, callback);
115 setCodeMirrorModeFromSelect(modes_select, filename_selector, fileEditor.cm, null);
143 116
144 117 // on entering the new filename set mode, from given extension
145 setCodeMirrorModeFromInput(
146 modes_select, filename_selector, myCodeMirror, callback);
147
148 // if the file is renderable set line wraps automatically
149 if (renderer !== ""){
150 var line_wrap = 'on';
151 $($('#line_wrap option[value="'+line_wrap+'"]')[0]).attr("selected", "selected");
152 setCodeMirrorLineWrap(myCodeMirror, true);
153 }
154 // on select line wraps change the editor
155 $('#line_wrap').on('change', function(e){
156 var selected = e.currentTarget;
157 var line_wraps = {'on': true, 'off': false}[selected.value];
158 setCodeMirrorLineWrap(myCodeMirror, line_wraps)
159 });
118 setCodeMirrorModeFromInput(modes_select, filename_selector, fileEditor.cm, null);
160 119
161 // render preview/edit button
162 if (mimetype === 'text/x-rst' || mimetype === 'text/plain') {
163 $('#render_preview').removeClass('hidden');
164 }
165 $('#render_preview').on('click', function(e){
166 if($(this).hasClass('preview')){
167 $(this).removeClass('preview');
168 $(this).html("${_('Edit')}");
169 $('#editor_preview').show();
170 $(myCodeMirror.getWrapperElement()).hide();
120 });
171 121
172 var possible_renderer = {
173 'rst':'rst',
174 'markdown':'markdown',
175 'gfm': 'markdown'}[myCodeMirror.getMode().name];
176 var _text = myCodeMirror.getValue();
177 var _renderer = possible_renderer || DEFAULT_RENDERER;
178 var post_data = {'text': _text, 'renderer': _renderer, 'csrf_token': CSRF_TOKEN};
179 $('#editor_preview').html(_gettext('Loading ...'));
180 var url = pyroutes.url('repo_commit_comment_preview',
181 {'repo_name': '${c.repo_name}',
182 'commit_id': '${c.commit.raw_id}'});
183 ajaxPOST(url, post_data, function(o){
184 $('#editor_preview').html(o);
185 })
186 }
187 else{
188 $(this).addClass('preview');
189 $(this).html("${_('Preview')}");
190 $('#editor_preview').hide();
191 $(myCodeMirror.getWrapperElement()).show();
192 }
193 });
194 122
195 })
196 123 </script>
197 124 </%def>
@@ -1,7 +1,7 b''
1 1 <%def name="title(*args)">
2 ${_('%s Files') % c.repo_name}
2 ${_('{} Files').format(c.repo_name)}
3 3 %if hasattr(c,'file'):
4 &middot; ${h.safe_unicode(c.file.path) or '\\'}
4 &middot; ${(h.safe_unicode(c.file.path) or '\\')}
5 5 %endif
6 6
7 7 %if c.rhodecode_name:
@@ -9,47 +9,26 b''
9 9 %endif
10 10 </%def>
11 11
12 <div id="pjax-content" data-title="${self.title()}">
12 <div>
13
13 14 <div class="summary-detail">
14 15 <div class="summary-detail-header">
15 <div class="breadcrumbs files_location">
16 <h4>
17 ${_('Location')}: ${h.files_breadcrumbs(c.repo_name,c.commit.raw_id,c.file.path)}
18 %if c.annotate:
19 - ${_('annotation')}
20 %endif
21 </h4>
22 </div>
23 <div class="btn-collapse" data-toggle="summary-details">
24 ${_('Show More')}
25 </div>
16
26 17 </div><!--end summary-detail-header-->
27 18
28 19 % if c.file.is_submodule():
29 20 <span class="submodule-dir">Submodule ${h.escape(c.file.name)}</span>
30 21 % elif c.file.is_dir():
31 <%include file='file_tree_detail.mako'/>
22 <%include file='files_tree_header.mako'/>
32 23 % else:
33 <%include file='files_detail.mako'/>
24 <%include file='files_source_header.mako'/>
34 25 % endif
35 26
36 27 </div> <!--end summary-detail-->
37 <script>
38 // set the pageSource variable
39 var fileSourcePage = ${c.file_source_page};
40 </script>
41 28 % if c.file.is_dir():
42 <div id="commit-stats" class="sidebar-right">
43 <%include file='file_tree_author_box.mako'/>
44 </div>
45
46 29 <%include file='files_browser.mako'/>
47 30 % else:
48 <div id="file_authors" class="sidebar-right">
49 <%include file='file_authors_box.mako'/>
50 </div>
51
52 31 <%include file='files_source.mako'/>
53 32 % endif
54 33
55 </div> No newline at end of file
34 </div>
@@ -1,81 +1,110 b''
1 1 <%namespace name="sourceblock" file="/codeblocks/source.mako"/>
2 2
3 <div id="codeblock" class="codeblock">
4 <div class="codeblock-header">
5 <div class="stats">
6 <span class="stats-filename">
7 <strong>
8 <i class="icon-file-text"></i>
9 ${c.file.unicode_path_safe}
10 </strong>
11 </span>
12 <span class="item last"><i class="tooltip icon-clipboard clipboard-action" data-clipboard-text="${c.f_path}" title="${_('Copy the full path')}"></i></span>
13 <br/>
3 <div id="codeblock" class="browserblock">
4 <div class="browser-header">
5 <div class="browser-nav">
6 <div class="pull-left">
7 ## loads the history for a file
8 ${h.hidden('file_refs_filter')}
9 </div>
10
11 <div class="pull-right">
12
13 ## Download
14 % if c.lf_node:
15 <a class="btn btn-default" href="${h.route_path('repo_file_download',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path, _query=dict(lf=1))}">
16 ${_('Download largefile')}
17 </a>
18 % else:
19 <a class="btn btn-default" href="${h.route_path('repo_file_download',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path)}">
20 ${_('Download file')}
21 </a>
22 % endif
14 23
24 %if h.HasRepoPermissionAny('repository.write','repository.admin')(c.repo_name):
25 ## on branch head, can edit files
26 %if c.on_branch_head and c.branch_or_raw_id:
27 ## binary files are delete only
28 % if c.file.is_binary:
29 ${h.link_to(_('Edit'), '#Edit', class_="btn btn-default disabled tooltip", title=_('Editing binary files not allowed'))}
30 ${h.link_to(_('Delete'), h.route_path('repo_files_remove_file',repo_name=c.repo_name,commit_id=c.branch_or_raw_id,f_path=c.f_path),class_="btn btn-danger")}
31 % else:
32 <a class="btn btn-default" href="${h.route_path('repo_files_edit_file',repo_name=c.repo_name,commit_id=c.branch_or_raw_id,f_path=c.f_path)}">
33 ${_('Edit on branch: ')}<code>${c.branch_name}</code>
34 </a>
35
36 <a class="btn btn-danger" href="${h.route_path('repo_files_remove_file',repo_name=c.repo_name,commit_id=c.branch_or_raw_id,f_path=c.f_path)}">
37 ${_('Delete')}
38 </a>
39 % endif
40 ## not on head, forbid all
41 % else:
42 ${h.link_to(_('Edit'), '#Edit', class_="btn btn-default disabled tooltip", title=_('Editing files allowed only when on branch head commit'))}
43 ${h.link_to(_('Delete'), '#Delete', class_="btn btn-default btn-danger disabled tooltip", title=_('Deleting files allowed only when on branch head commit'))}
44 % endif
45 %endif
46
47 </div>
48 </div>
49 <div id="file_history_container"></div>
50
51 </div>
52 </div>
53
54 <div class="codeblock">
55 <div class=" codeblock-header">
56 <div class="file-filename">
57 <i class="icon-file"></i> ${c.file}
58 </div>
59
60 <div class="file-stats">
61
62 <div class="stats-info">
63 <span class="stats-first-item">${c.file.lines()[0]} ${_ungettext('line', 'lines', c.file.lines()[0])}</span>
64
65 <span> | ${h.format_byte_size_binary(c.file.size)}</span>
15 66 % if c.lf_node:
16 67 <span title="${_('This file is a pointer to large binary file')}"> | ${_('LargeFile')} ${h.format_byte_size_binary(c.lf_node.size)} </span>
17 68 % endif
18
19 <span class="stats-first-item">${c.file.lines()[0]} ${_ungettext('line', 'lines', c.file.lines()[0])}</span>
20 <span> | ${h.format_byte_size_binary(c.file.size)}</span>
21 69 <span> | ${c.file.mimetype} </span>
22 70 <span> | ${h.get_lexer_for_filenode(c.file).__class__.__name__}</span>
23
71 </div>
72 </div>
24 73 </div>
25 <div class="buttons">
26 <a id="file_history_overview" href="#">
27 ${_('History')}
28 </a>
29 <a id="file_history_overview_full" style="display: none" href="${h.route_path('repo_changelog_file',repo_name=c.repo_name, commit_id=c.commit.raw_id, f_path=c.f_path)}">
30 ${_('Show Full History')}
31 </a> |
32 %if c.annotate:
33 ${h.link_to(_('Source'), h.route_path('repo_files', repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path))}
34 %else:
35 ${h.link_to(_('Annotation'), h.route_path('repo_files:annotated',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path))}
36 %endif
37 | ${h.link_to(_('Raw'), h.route_path('repo_file_raw',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path))}
38 |
39 % if c.lf_node:
40 <a href="${h.route_path('repo_file_download',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path, _query=dict(lf=1))}">
41 ${_('Download largefile')}
42 </a>
43 % else:
44 <a href="${h.route_path('repo_file_download',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path)}">
45 ${_('Download')}
46 </a>
47 % endif
74
75 <div class="path clear-fix">
76 <div class="pull-left">
77 ${h.files_breadcrumbs(c.repo_name,c.commit.raw_id,c.file.path, request.GET.get('at'))}
78 </div>
48 79
49 %if h.HasRepoPermissionAny('repository.write','repository.admin')(c.repo_name):
50 |
51 %if c.on_branch_head and c.branch_or_raw_id and not c.file.is_binary:
52 <a href="${h.route_path('repo_files_edit_file',repo_name=c.repo_name,commit_id=c.branch_or_raw_id,f_path=c.f_path, _anchor='edit')}">
53 ${_('Edit on Branch:{}').format(c.branch_name)}
54 </a>
55 | <a class="btn-danger btn-link" href="${h.route_path('repo_files_remove_file',repo_name=c.repo_name,commit_id=c.branch_or_raw_id,f_path=c.f_path, _anchor='edit')}">${_('Delete')}
56 </a>
57 %elif c.on_branch_head and c.branch_or_raw_id and c.file.is_binary:
58 ${h.link_to(_('Edit'), '#', class_="btn btn-link disabled tooltip", title=_('Editing binary files not allowed'))}
59 | ${h.link_to(_('Delete'), h.route_path('repo_files_remove_file',repo_name=c.repo_name,commit_id=c.branch_or_raw_id,f_path=c.f_path, _anchor='edit'),class_="btn-danger btn-link")}
60 %else:
61 ${h.link_to(_('Edit'), '#', class_="btn btn-link disabled tooltip", title=_('Editing files allowed only when on branch head commit'))}
62 | ${h.link_to(_('Delete'), '#', class_="btn btn-danger btn-link disabled tooltip", title=_('Deleting files allowed only when on branch head commit'))}
63 %endif
64 %endif
80 <div class="pull-right stats">
81 <a id="file_history_overview" href="#loadHistory">
82 ${_('History')}
83 </a>
84 |
85 %if c.annotate:
86 ${h.link_to(_('Source'), h.route_path('repo_files', repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path))}
87 %else:
88 ${h.link_to(_('Annotation'), h.route_path('repo_files:annotated',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path))}
89 %endif
90 | ${h.link_to(_('Raw'), h.route_path('repo_file_raw',repo_name=c.repo_name,commit_id=c.commit.raw_id,f_path=c.f_path))}
91
92 </div>
93 <div class="clear-fix"></div>
65 94 </div>
66 </div>
67 <div id="file_history_container"></div>
68 <div class="code-body">
69 %if c.file.is_binary:
70 <% rendered_binary = h.render_binary(c.repo_name, c.file)%>
71 % if rendered_binary:
72 ${rendered_binary}
73 % else:
74 <div>
75 ${_('Binary file (%s)') % c.file.mimetype}
76 </div>
77 % endif
78 %else:
95
96 <div class="code-body clear-fix ">
97
98 %if c.file.is_binary:
99 <% rendered_binary = h.render_binary(c.repo_name, c.file)%>
100 % if rendered_binary:
101 ${rendered_binary}
102 % else:
103 <div>
104 ${_('Binary file (%s)') % c.file.mimetype}
105 </div>
106 % endif
107 %else:
79 108 % if c.file.size < c.visual.cut_off_limit_file:
80 109 %if c.renderer and not c.annotate:
81 110 ## pick relative url based on renderer
@@ -106,7 +135,8 b''
106 135 %endif
107 136 %endif
108 137 </div>
109 </div>
138
139 </div>
110 140
111 141 <script type="text/javascript">
112 142 % if request.GET.get('mark'):
@@ -1,69 +1,61 b''
1 <%namespace name="base" file="/base/base.mako"/>
1 2 <%namespace name="file_base" file="/files/base.mako"/>
2 3
3 <div class="fieldset collapsable-content no-hide" data-toggle="summary-details">
4 <div class="left-label">
5 ${_('Commit Description')}:
6 </div>
7 <div class="commit right-content truncate-wrap">${h.urlify_commit_message(h.chop_at_smart(c.commit.message, '\n', suffix_if_chopped='...'), c.repo_name)}</div>
8 </div>
4 <div class="summary">
5 <div class="fieldset">
6 <div class="left-content">
7
8 <div class="left-content-avatar">
9 ${base.gravatar(c.file_last_commit.author_email, 30)}
10 </div>
11
12 <div class="left-content-message">
13 <div class="fieldset collapsable-content no-hide" data-toggle="summary-details">
14 <div class="commit truncate-wrap">${h.urlify_commit_message(h.chop_at_smart(c.commit.message, '\n', suffix_if_chopped='...'), c.repo_name)}</div>
15 </div>
16
17 <div class="fieldset collapsable-content" data-toggle="summary-details">
18 <div class="commit">${h.urlify_commit_message(c.commit.message,c.repo_name)}</div>
19 </div>
20
21 <div class="fieldset" data-toggle="summary-details">
22 <div class="" id="file_authors">
23 ## loads single author, or ALL
24 <%include file='file_authors_box.mako'/>
25 </div>
26 </div>
27 </div>
9 28
10 <div class="fieldset collapsable-content" data-toggle="summary-details">
11 <div class="left-label">
12 ${_('Commit Description')}:
13 </div>
14 <div class="commit right-content">${h.urlify_commit_message(c.commit.message,c.repo_name)}</div>
15 </div>
29 <div class="fieldset collapsable-content" data-toggle="summary-details">
30 <div class="left-label-summary-files">
31 <p>${_('File last commit')}</p>
32 <div class="right-label-summary">
33 <code><a href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.file_last_commit.raw_id)}">${h.show_id(c.file_last_commit)}</a></code>
16 34
35 ${file_base.refs(c.file_last_commit)}
36 </div>
37 </div>
38 </div>
39 </div>
17 40
18 <div class="fieldset " data-toggle="summary-details">
19 <div class="left-label">
20 ${_('References')}:
21 </div>
22 <div class="right-content">
23 <div class="tags tags-main">
24 <code><a href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.commit.raw_id)}">${h.show_id(c.commit)}</a></code>
25 ${file_base.refs(c.commit)}
41 <div class="right-content">
42 <div data-toggle="summary-details">
43 <div class="tags commit-info tags-main">
44 <code><a href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.commit.raw_id)}">${h.show_id(c.commit)}</a></code>
45 ${file_base.refs(c.commit)}
46 </div>
47 </div>
26 48 </div>
49
50 <div class="clear-fix"></div>
51
52 <div class="btn-collapse" data-toggle="summary-details">
53 ${_('Show More')}
54 </div>
55
27 56 </div>
28 57 </div>
29 58
30 <div class="fieldset collapsable-content" data-toggle="summary-details">
31 <div class="left-label">
32 ${_('File last commit')}:
33 </div>
34 <div class="right-content">
35 <div class="tags">
36 <code><a href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.file_last_commit.raw_id)}">${h.show_id(c.file_last_commit)}</a></code>
37
38 ${file_base.refs(c.file_last_commit)}
39 </div>
40 </div>
41 </div>
42
43
44 <div class="fieldset collapsable-content" data-toggle="summary-details">
45 <div class="left-label">
46 ${_('Show/Diff file')}:
47 </div>
48 <div class="right-content">
49 ${h.hidden('diff1')}
50 ${h.hidden('diff2',c.commit.raw_id)}
51 ${h.hidden('annotate', c.annotate)}
52 </div>
53 </div>
54
55
56 <div class="fieldset collapsable-content" data-toggle="summary-details">
57 <div class="left-label">
58 ${_('Action')}:
59 </div>
60 <div class="right-content">
61 ${h.submit('diff_to_commit',_('Diff to Commit'),class_="btn disabled",disabled="true")}
62 ${h.submit('show_at_commit',_('Show at Commit'),class_="btn disabled",disabled="true")}
63 </div>
64 </div>
65
66
67 59 <script>
68 60 collapsableContent();
69 </script> No newline at end of file
61 </script>
@@ -1,37 +1,46 b''
1 <%namespace name="base" file="/base/base.mako"/>
1 2 <%namespace name="file_base" file="/files/base.mako"/>
2 3
3 <div class="fieldset collapsable-content no-hide" data-toggle="summary-details">
4 <div class="left-label">
5 ${_('Description')}:
6 </div>
7 <div class="commit right-content truncate-wrap">${h.urlify_commit_message(h.chop_at_smart(c.commit.message, '\n', suffix_if_chopped='...'), c.repo_name)}</div>
8 </div>
4 <div class="summary">
5 <div class="fieldset">
6 <div class="left-content">
7
8 <div class="left-content-avatar">
9 ${base.gravatar(c.commit.author_email, 30)}
10 </div>
9 11
10 <div class="fieldset collapsable-content" data-toggle="summary-details">
11 <div class="left-label">
12 ${_('Description')}:
13 </div>
14 <div class="commit right-content">${h.urlify_commit_message(c.commit.message,c.repo_name)}</div>
15 </div>
12 <div class="left-content-message">
13 <div class="fieldset collapsable-content no-hide" data-toggle="summary-details">
14 <div class="commit truncate-wrap">${h.urlify_commit_message(h.chop_at_smart(c.commit.message, '\n', suffix_if_chopped='...'), c.repo_name)}</div>
15 </div>
16
17 <div class="fieldset collapsable-content" data-toggle="summary-details">
18 <div class="commit">${h.urlify_commit_message(c.commit.message,c.repo_name)}</div>
19 </div>
16 20
17
21 <div class="fieldset clear-fix">
22 <span class="commit-author">${h.link_to_user(c.commit.author)}</span><span class="commit-date"> - ${h.age_component(c.commit.date)}</span>
23 </div>
24 </div>
25 </div>
18 26
19 <div class="fieldset">
20 <div class="left-label">
21 ${_('References')}:
22 </div>
23 <div class="right-content">
24 <div class="tags">
25 <code>
26 <a href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.commit.raw_id)}">${h.show_id(c.commit)}</a>
27 </code>
27 <div class="right-content">
28 <div class="tags commit-info">
29 <code>
30 <a href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=c.commit.raw_id)}">${h.show_id(c.commit)}</a>
31 </code>
28 32
29 ${file_base.refs(c.commit)}
33 ${file_base.refs(c.commit)}
34 </div>
35 </div>
36
37 <div class="clear-fix"></div>
38
39 <div class="btn-collapse" data-toggle="summary-details">
40 ${_('Show More')}
30 41 </div>
31 42 </div>
32 43 </div>
33
34
35 44 <script>
36 45 collapsableContent();
37 46 </script>
@@ -20,10 +20,6 b''
20 20
21 21 <%def name="main()">
22 22 <div class="box">
23 <div class="title">
24 ${self.repo_page_title(c.rhodecode_db_repo)}
25 </div>
26
27 23 ${h.secure_form(h.route_path('repo_fork_create',repo_name=c.rhodecode_db_repo.repo_name), request=request)}
28 24 <div class="form">
29 25 <!-- fields -->
@@ -8,9 +8,7 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 ${_('Forks')}
13 </%def>
11 <%def name="breadcrumbs_links()"></%def>
14 12
15 13 <%def name="menu_bar_nav()">
16 14 ${self.menu_items(active='repositories')}
@@ -23,7 +21,7 b''
23 21 <%def name="main()">
24 22 <div class="box">
25 23 <div class="title">
26 ${self.repo_page_title(c.rhodecode_db_repo)}
24
27 25 <ul class="links">
28 26 <li>
29 27 <a class="btn btn-small btn-success" href="${h.route_path('repo_fork_new',repo_name=c.repo_name)}">
@@ -12,32 +12,15 b''
12 12 <div class="box">
13 13 <!-- box / title -->
14 14 <div class="title">
15 % if c.repo_group:
16 ${self.repo_group_page_title(c.repo_group)}
17 ## context actions
18 <div>
19 <ul class="links icon-only-links block-right">
20 <li></li>
21 </ul>
22 </div>
23 % endif
24
25 15 %if c.rhodecode_user.username != h.DEFAULT_USER:
26 16 <div class="block-right">
27 <%
28 is_admin = h.HasPermissionAny('hg.admin')('can create repos index page')
29 create_repo = h.HasPermissionAny('hg.create.repository')('can create repository index page')
30 create_repo_group = h.HasPermissionAny('hg.repogroup.create.true')('can create repository groups index page')
31 create_user_group = h.HasPermissionAny('hg.usergroup.create.true')('can create user groups index page')
32 %>
33
34 17 %if not c.repo_group:
35 18 ## no repository group context here
36 %if is_admin or create_repo:
19 %if c.is_super_admin or c.can_create_repo:
37 20 <a href="${h.route_path('repo_new')}" class="btn btn-small btn-success btn-primary">${_('Add Repository')}</a>
38 21 %endif
39 22
40 %if is_admin or create_repo_group:
23 %if c.is_super_admin or c.can_create_repo_group:
41 24 <a href="${h.route_path('repo_group_new')}" class="btn btn-small btn-default">${_(u'Add Repository Group')}</a>
42 25 %endif
43 26 %endif
@@ -79,13 +62,16 b''
79 62 order: [[ 0, "asc" ]],
80 63 columns: [
81 64 { data: {"_": "name",
82 "sort": "name_raw"}, title: "${_('Name')}", className: "td-componentname" },
65 "sort": "name_raw"}, title: "${_('Name')}", className: "truncate-wrap td-grid-name" },
83 66 { data: 'menu', "bSortable": false, className: "quick_repo_menu" },
84 67 { data: {"_": "desc",
85 68 "sort": "desc"}, title: "${_('Description')}", className: "td-description" },
86 69 { data: {"_": "last_change",
87 70 "sort": "last_change_raw",
88 71 "type": Number}, title: "${_('Last Change')}", className: "td-time" },
72 { data: {"_": "last_changeset",
73 "sort": "last_changeset_raw",
74 "type": Number}, title: "", className: "td-hash" },
89 75 { data: {"_": "owner",
90 76 "sort": "owner"}, title: "${_('Owner')}", className: "td-user" }
91 77 ],
@@ -109,7 +95,7 b''
109 95 pageLength: ${c.visual.dashboard_items},
110 96 columns: [
111 97 { data: {"_": "name",
112 "sort": "name_raw"}, title: "${_('Name')}", className: "truncate-wrap td-componentname" },
98 "sort": "name_raw"}, title: "${_('Name')}", className: "truncate-wrap td-grid-name" },
113 99 { data: 'menu', "bSortable": false, className: "quick_repo_menu" },
114 100 { data: {"_": "desc",
115 101 "sort": "desc"}, title: "${_('Description')}", className: "td-description" },
@@ -14,11 +14,13 b''
14 14 <div id="header-inner" class="title">
15 15 <div id="logo">
16 16 <div class="logo-wrapper">
17 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-216x60.png')}" alt="RhodeCode"/></a>
17 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-60x60.png')}" alt="RhodeCode"/></a>
18 18 </div>
19 %if c.rhodecode_name:
20 <div class="branding">- ${h.branding(c.rhodecode_name)}</div>
21 %endif
19 % if c.rhodecode_name:
20 <div class="branding">
21 <a href="${h.route_path('home')}">${h.branding(c.rhodecode_name)}</a>
22 </div>
23 % endif
22 24 </div>
23 25 </div>
24 26 </div>
@@ -14,11 +14,13 b''
14 14 <div id="header-inner" class="title">
15 15 <div id="logo">
16 16 <div class="logo-wrapper">
17 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-216x60.png')}" alt="RhodeCode"/></a>
17 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-60x60.png')}" alt="RhodeCode"/></a>
18 18 </div>
19 %if c.rhodecode_name:
20 <div class="branding">- ${h.branding(c.rhodecode_name)}</div>
21 %endif
19 % if c.rhodecode_name:
20 <div class="branding">
21 <a href="${h.route_path('home')}">${h.branding(c.rhodecode_name)}</a>
22 </div>
23 % endif
22 24 </div>
23 25 </div>
24 26 </div>
@@ -5,9 +5,7 b''
5 5 ${c.repo_name} ${_('New pull request')}
6 6 </%def>
7 7
8 <%def name="breadcrumbs_links()">
9 ${_('New pull request')}
10 </%def>
8 <%def name="breadcrumbs_links()"></%def>
11 9
12 10 <%def name="menu_bar_nav()">
13 11 ${self.menu_items(active='repositories')}
@@ -19,13 +17,9 b''
19 17
20 18 <%def name="main()">
21 19 <div class="box">
22 <div class="title">
23 ${self.repo_page_title(c.rhodecode_db_repo)}
24 </div>
25
26 20 ${h.secure_form(h.route_path('pullrequest_create', repo_name=c.repo_name, _query=request.GET.mixed()), id='pull_request_form', request=request)}
27 21
28 ${self.breadcrumbs()}
22 ${_('New pull request')}
29 23
30 24 <div class="box pr-summary">
31 25
@@ -28,6 +28,9 b''
28 28 </span>
29 29 </li>
30 30 % endfor
31 <li>
32 Try <a href="${h.current_route_path(request, force_refresh=1)}">forced recheck</a> of the merge workspace in case current status seems wrong.
33 </li>
31 34 </ul>
32 35 % endif
33 36
@@ -38,10 +38,6 b''
38 38 </script>
39 39 <div class="box">
40 40
41 <div class="title">
42 ${self.repo_page_title(c.rhodecode_db_repo)}
43 </div>
44
45 41 ${self.breadcrumbs()}
46 42
47 43 <div class="box pr-summary">
@@ -76,7 +72,7 b''
76 72 ## branch link is only valid if it is a branch
77 73 <span class="tag">
78 74 %if c.pull_request.source_ref_parts.type == 'branch':
79 <a href="${h.route_path('repo_changelog', repo_name=c.pull_request.source_repo.repo_name, _query=dict(branch=c.pull_request.source_ref_parts.name))}">${c.pull_request.source_ref_parts.type}: ${c.pull_request.source_ref_parts.name}</a>
75 <a href="${h.route_path('repo_commits', repo_name=c.pull_request.source_repo.repo_name, _query=dict(branch=c.pull_request.source_ref_parts.name))}">${c.pull_request.source_ref_parts.type}: ${c.pull_request.source_ref_parts.name}</a>
80 76 %else:
81 77 ${c.pull_request.source_ref_parts.type}: ${c.pull_request.source_ref_parts.name}
82 78 %endif
@@ -112,7 +108,7 b''
112 108 ## branch link is only valid if it is a branch
113 109 <span class="tag">
114 110 %if c.pull_request.target_ref_parts.type == 'branch':
115 <a href="${h.route_path('repo_changelog', repo_name=c.pull_request.target_repo.repo_name, _query=dict(branch=c.pull_request.target_ref_parts.name))}">${c.pull_request.target_ref_parts.type}: ${c.pull_request.target_ref_parts.name}</a>
111 <a href="${h.route_path('repo_commits', repo_name=c.pull_request.target_repo.repo_name, _query=dict(branch=c.pull_request.target_ref_parts.name))}">${c.pull_request.target_ref_parts.type}: ${c.pull_request.target_ref_parts.name}</a>
116 112 %else:
117 113 ${c.pull_request.target_ref_parts.type}: ${c.pull_request.target_ref_parts.name}
118 114 %endif
@@ -7,9 +7,7 b''
7 7 %endif
8 8 </%def>
9 9
10 <%def name="breadcrumbs_links()">
11
12 </%def>
10 <%def name="breadcrumbs_links()"></%def>
13 11
14 12 <%def name="menu_bar_nav()">
15 13 ${self.menu_items(active='repositories')}
@@ -22,63 +20,36 b''
22 20
23 21
24 22 <%def name="main()">
25 <div class="box">
26 <div class="title">
27 ${self.repo_page_title(c.rhodecode_db_repo)}
28 23
29 <ul class="links">
24 <div class="box">
25 <div class="title">
26 <ul class="button-links">
27 <li class="btn ${('active' if c.active=='open' else '')}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0})}">${_('Opened')}</a></li>
28 <li class="btn ${('active' if c.active=='my' else '')}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'my':1})}">${_('Opened by me')}</a></li>
29 <li class="btn ${('active' if c.active=='awaiting' else '')}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'awaiting_review':1})}">${_('Awaiting review')}</a></li>
30 <li class="btn ${('active' if c.active=='awaiting_my' else '')}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'awaiting_my_review':1})}">${_('Awaiting my review')}</a></li>
31 <li class="btn ${('active' if c.active=='closed' else '')}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'closed':1})}">${_('Closed')}</a></li>
32 <li class="btn ${('active' if c.active=='source' else '')}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':1})}">${_('From this repo')}</a></li>
33 </ul>
34
35 <ul class="links">
36 % if c.rhodecode_user.username != h.DEFAULT_USER:
30 37 <li>
31 %if c.rhodecode_user.username != h.DEFAULT_USER:
32 38 <span>
33 39 <a id="open_new_pull_request" class="btn btn-small btn-success" href="${h.route_path('pullrequest_new',repo_name=c.repo_name)}">
34 40 ${_('Open new Pull Request')}
35 41 </a>
36 42 </span>
37 %endif
38 43 </li>
39 </ul>
40
41 ${self.breadcrumbs()}
42 </div>
44 % endif
45 </ul>
43 46
44 <div class="sidebar-col-wrapper">
45 ##main
46 <div class="sidebar">
47 <ul class="nav nav-pills nav-stacked">
48 <li class="${'active' if c.active=='open' else ''}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0})}">${_('Opened')}</a></li>
49 <li class="${'active' if c.active=='my' else ''}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'my':1})}">${_('Opened by me')}</a></li>
50 <li class="${'active' if c.active=='awaiting' else ''}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'awaiting_review':1})}">${_('Awaiting review')}</a></li>
51 <li class="${'active' if c.active=='awaiting_my' else ''}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'awaiting_my_review':1})}">${_('Awaiting my review')}</a></li>
52 <li class="${'active' if c.active=='closed' else ''}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':0,'closed':1})}">${_('Closed')}</a></li>
53 <li class="${'active' if c.active=='source' else ''}"><a href="${h.route_path('pullrequest_show_all',repo_name=c.repo_name, _query={'source':1})}">${_('From this repo')}</a></li>
54 </ul>
55 47 </div>
56 48
57 49 <div class="main-content-full-width">
58 <div class="panel panel-default">
59 <div class="panel-heading">
60 <h3 class="panel-title">
61 %if c.source:
62 ${_('Pull Requests from %(repo_name)s repository') % {'repo_name': c.repo_name}}
63 %elif c.closed:
64 ${_('Closed Pull Requests to repository %(repo_name)s') % {'repo_name': c.repo_name}}
65 %elif c.my:
66 ${_('Pull Requests to %(repo_name)s repository opened by me') % {'repo_name': c.repo_name}}
67 %elif c.awaiting_review:
68 ${_('Pull Requests to %(repo_name)s repository awaiting review') % {'repo_name': c.repo_name}}
69 %elif c.awaiting_my_review:
70 ${_('Pull Requests to %(repo_name)s repository awaiting my review') % {'repo_name': c.repo_name}}
71 %else:
72 ${_('Pull Requests to %(repo_name)s repository') % {'repo_name': c.repo_name}}
73 %endif
74 </h3>
75 </div>
76 <div class="panel-body panel-body-min-height">
77 <table id="pull_request_list_table" class="display"></table>
78 </div>
79 </div>
50 <table id="pull_request_list_table" class="display"></table>
80 51 </div>
81 </div>
52
82 53 </div>
83 54
84 55 <script type="text/javascript">
@@ -14,11 +14,13 b''
14 14 <div id="header-inner" class="title">
15 15 <div id="logo">
16 16 <div class="logo-wrapper">
17 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-216x60.png')}" alt="RhodeCode"/></a>
17 <a href="${h.route_path('home')}"><img src="${h.asset('images/rhodecode-logo-white-60x60.png')}" alt="RhodeCode"/></a>
18 18 </div>
19 %if c.rhodecode_name:
20 <div class="branding">- ${h.branding(c.rhodecode_name)}</div>
21 %endif
19 % if c.rhodecode_name:
20 <div class="branding">
21 <a href="${h.route_path('home')}">${h.branding(c.rhodecode_name)}</a>
22 </div>
23 % endif
22 24 </div>
23 25 </div>
24 26 </div>
@@ -37,9 +37,10 b''
37 37
38 38 <%def name="menu_bar_subnav()">
39 39 %if c.repo_name:
40 ${self.repo_menu(active='search')}
40 <% active_entry = {'content':'files', 'path':'files', 'commit':'commits'}.get(c.search_type, 'summary')%>
41 ${self.repo_menu(active=active_entry)}
41 42 %elif c.repo_group_name:
42 ${self.repo_group_menu(active='search')}
43 ${self.repo_group_menu(active='home')}
43 44 %endif
44 45 </%def>
45 46
@@ -56,22 +57,16 b''
56 57 </%def>
57 58
58 59 <%def name="repo_group_icon()">
59 <i class="icon-folder-close"></i>
60 <i class="icon-repo-group"></i>
60 61 </%def>
61 62
62 63 <%def name="main()">
63 64 <div class="box">
64 65 %if c.repo_name:
65 66 <!-- box / title -->
66 <div class="title">
67 ${self.repo_page_title(c.rhodecode_db_repo)}
68 </div>
69 67 ${h.form(h.route_path('search_repo',repo_name=c.repo_name),method='get')}
70 68 %elif c.repo_group_name:
71 69 <!-- box / title -->
72 <div class="title">
73 ${self.repo_group_page_title(c.repo_group)}
74 </div>
75 70 ${h.form(h.route_path('search_repo_group',repo_group_name=c.repo_group_name),method='get')}
76 71 %else:
77 72 <!-- box / title -->
@@ -58,65 +58,50 b''
58 58 %>
59 59 ## search results are additionally filtered, and this check is just a safe gate
60 60 % if c.rhodecode_user.is_admin or h.HasRepoPermissionAny('repository.write','repository.read','repository.admin')(entry['repository'], 'search results content check'):
61 <div id="codeblock" class="codeblock">
62 <div class="codeblock-header">
63 <h1>
64 <% repo_type = entry.get('repo_type') or h.get_repo_type_by_name(entry.get('repository')) %>
65 ${search.repo_icon(repo_type)}
66 ${h.link_to(entry['repository'], h.route_path('repo_summary',repo_name=entry['repository']))}
67 </h1>
68 ## level 1
69 <div class="file-container">
61 <div class="codeblock">
62 <h1>
63 <% repo_type = entry.get('repo_type') or h.get_repo_type_by_name(entry.get('repository')) %>
64 ${search.repo_icon(repo_type)}
65 ${h.link_to(entry['repository'], h.route_path('repo_summary', repo_name=entry['repository']))}
66 </h1>
70 67
71 <div class="pull-left">
72 <span class="stats-filename">
73 <strong>
74 <i class="icon-file-text"></i>
75 ${h.link_to(h.literal(entry['f_path']), h.route_path('repo_files',repo_name=entry['repository'],commit_id=entry.get('commit_id', 'tip'),f_path=entry['f_path']))}
76 </strong>
77 </span>
78 <span class="item last">
79 <i class="tooltip icon-clipboard clipboard-action" data-clipboard-text="${entry['f_path']}" title="${_('Copy the full path')}"></i>
80 </span>
68 <div class="codeblock-header">
69
70 <div class="file-filename">
71 <i class="icon-file"></i> ${entry['f_path'].split('/')[-1]}
81 72 </div>
82 73
83 <div class="pull-right">
84 <div class="buttons">
85 <a id="file_history_overview_full" href="${h.route_path('repo_changelog_file',repo_name=entry.get('repository',''),commit_id=entry.get('commit_id', 'tip'),f_path=entry.get('f_path',''))}">
86 ${_('Show Full History')}
87 </a>
88 | ${h.link_to(_('Annotation'), h.route_path('repo_files:annotated', repo_name=entry.get('repository',''),commit_id=entry.get('commit_id', 'tip'),f_path=entry.get('f_path','')))}
89 | ${h.link_to(_('Raw'), h.route_path('repo_file_raw', repo_name=entry.get('repository',''),commit_id=entry.get('commit_id', 'tip'),f_path=entry.get('f_path','')))}
90 | ${h.link_to(_('Download'), h.route_path('repo_file_download',repo_name=entry.get('repository',''),commit_id=entry.get('commit_id', 'tip'),f_path=entry.get('f_path','')))}
91 </div>
74 <div class="file-stats">
75 <div class="stats-info">
76 <span class="stats-first-item">
77 ${entry.get('lines', 0.)} ${_ungettext('line', 'lines', entry.get('lines', 0.))}
78 (${len(matching_lines)} ${_ungettext('matched', 'matched', len(matching_lines))})
79 </span>
80 <span>
81 % if entry.get('size'):
82 | ${h.format_byte_size_binary(entry['size'])}
83 % endif
84 </span>
85 <span>
86 % if entry.get('mimetype'):
87 | ${entry.get('mimetype', "unknown mimetype")}
88 % endif
89 </span>
90 </div>
91 </div>
92 </div>
93
94 <div class="path clear-fix">
95 <div class="pull-left">
96 ${h.files_breadcrumbs(entry['repository'],entry.get('commit_id', 'tip'),entry['f_path'], linkify_last_item=True)}
92 97 </div>
93 98
94 </div>
95 ## level 2
96 <div class="file-container">
97
98 <div class="pull-left">
99 <span class="stats-first-item">
100 %if entry.get('lines'):
101 ${entry.get('lines', 0.)} ${_ungettext('line', 'lines', entry.get('lines', 0.))}
102 (${len(matching_lines)} ${_ungettext('matched', 'matched', len(matching_lines))})
103 %endif
104 </span>
105
106 <span>
107 %if entry.get('size'):
108 | ${h.format_byte_size_binary(entry['size'])}
109 %endif
110 </span>
111
112 <span>
113 %if entry.get('mimetype'):
114 | ${entry.get('mimetype', "unknown mimetype")}
115 %endif
116 </span>
117 </div>
118
119 <div class="pull-right">
99 <div class="pull-right stats">
100 ## <a id="file_history_overview_full" href="${h.route_path('repo_commits_file',repo_name=entry.get('repository',''),commit_id=entry.get('commit_id', 'tip'),f_path=entry.get('f_path',''))}">
101 ## ${_('Show Full History')}
102 ## </a>
103 ## | ${h.link_to(_('Annotation'), h.route_path('repo_files:annotated', repo_name=entry.get('repository',''),commit_id=entry.get('commit_id', 'tip'),f_path=entry.get('f_path','')))}
104 ## | ${h.link_to(_('Raw'), h.route_path('repo_file_raw', repo_name=entry.get('repository',''),commit_id=entry.get('commit_id', 'tip'),f_path=entry.get('f_path','')))}
120 105 <div class="search-tags">
121 106
122 107 <% repo_group = entry.get('repository_group')%>
@@ -135,13 +120,13 b''
135 120 </span>
136 121 % endif
137 122 </div>
138 </div>
139
140 </div>
141 123
124 </div>
125 <div class="clear-fix"></div>
142 126 </div>
143 <div class="code-body search-code-body">
127
144 128
129 <div class="code-body search-code-body clear-fix">
145 130 ${highlight_text_file(
146 131 has_matched_content=has_matched_content,
147 132 file_content=file_content,
@@ -1,29 +1,51 b''
1 <%namespace name="base" file="/base/base.mako"/>
2
1 3 <%def name="refs_counters(branches, closed_branches, tags, bookmarks)">
2 <span class="branchtag tag">
4 <span class="summary-branchtag summary-tag">
3 5 <a href="${h.route_path('branches_home',repo_name=c.repo_name)}" class="childs">
4 <i class="icon-branch"></i>${_ungettext(
5 '%(num)s Branch','%(num)s Branches', len(branches)) % {'num': len(branches)}}</a>
6 <i class="icon-branch"></i>
7 % if len(branches) == 1:
8 <span>${len(branches)}</span> ${_('Branch')}
9 % else:
10 <span>${len(branches)}</span> ${_('Branches')}
11 % endif
12 </a>
6 13 </span>
7 14
8 15 %if closed_branches:
9 <span class="branchtag tag">
16 <span class="summary-branchtag summary-tag">
10 17 <a href="${h.route_path('branches_home',repo_name=c.repo_name)}" class="childs">
11 <i class="icon-branch"></i>${_ungettext(
12 '%(num)s Closed Branch', '%(num)s Closed Branches', len(closed_branches)) % {'num': len(closed_branches)}}</a>
18 <i class="icon-branch"></i>
19 % if len(closed_branches) == 1:
20 <span>${len(closed_branches)}</span> ${_('Closed Branch')}
21 % else:
22 <span>${len(closed_branches)}</span> ${_('Closed Branches')}
23 % endif
24 </a>
13 25 </span>
14 26 %endif
15 27
16 <span class="tagtag tag">
28 <span class="summary-tagtag summary-tag">
17 29 <a href="${h.route_path('tags_home',repo_name=c.repo_name)}" class="childs">
18 <i class="icon-tag"></i>${_ungettext(
19 '%(num)s Tag', '%(num)s Tags', len(tags)) % {'num': len(tags)}}</a>
30 <i class="icon-tag"></i>
31 % if len(tags) == 1:
32 <span>${len(tags)}</span> ${_('Tag')}
33 % else:
34 <span>${len(tags)}</span> ${_('Tags')}
35 % endif
36 </a>
20 37 </span>
21 38
22 39 %if bookmarks:
23 <span class="booktag tag">
40 <span class="summary-booktag summary-tag">
24 41 <a href="${h.route_path('bookmarks_home',repo_name=c.repo_name)}" class="childs">
25 <i class="icon-bookmark"></i>${_ungettext(
26 '%(num)s Bookmark', '%(num)s Bookmarks', len(bookmarks)) % {'num': len(bookmarks)}}</a>
42 <i class="icon-bookmark"></i>
43 % if len(bookmarks) == 1:
44 <span>${len(bookmarks)}</span> ${_('Bookmark')}
45 % else:
46 <span>${len(bookmarks)}</span> ${_('Bookmarks')}
47 % endif
48 </a>
27 49 </span>
28 50 %endif
29 51 </%def>
@@ -32,19 +54,8 b''
32 54 <% summary = lambda n:{False:'summary-short'}.get(n) %>
33 55
34 56 <div id="summary-menu-stats" class="summary-detail">
35 <div class="summary-detail-header">
36 <div class="breadcrumbs files_location">
37 <h4>
38 ${breadcrumbs_links}
39 </h4>
40 </div>
41 <div id="summary_details_expand" class="btn-collapse" data-toggle="summary-details">
42 ${_('Show More')}
43 </div>
44 </div>
45
46 57 <div class="fieldset">
47
58 <div class="left-content">
48 59 <div class="left-clone">
49 60 <select id="clone_option" name="clone_option">
50 61 <option value="http" selected="selected">HTTP</option>
@@ -54,6 +65,7 b''
54 65 % endif
55 66 </select>
56 67 </div>
68
57 69 <div class="right-clone">
58 70 <%
59 71 maybe_disabled = ''
@@ -79,14 +91,9 b''
79 91 % if maybe_disabled:
80 92 <p class="help-block">${_('SVN Protocol is disabled. To enable it, see the')} <a href="${h.route_url('enterprise_svn_setup')}" target="_blank">${_('documentation here')}</a>.</p>
81 93 % endif
82
83 94 </div>
84 </div>
95 </div>
85 96
86 <div class="fieldset">
87 <div class="left-label-summary">
88 &nbsp;
89 </div>
90 97 <div class="right-content">
91 98 <div class="commit-info">
92 99 <div class="tags">
@@ -103,32 +110,99 b''
103 110 % endif
104 111
105 112 ## commits
106 <span class="tag">
113 <span class="summary-tag">
107 114 % if commit_rev == -1:
108 ${_ungettext('%(num)s Commit', '%(num)s Commits', 0) % {'num': 0}}
115 <i class="icon-history"></i>
116 % if commit_rev == -1:
117 <span>0</span> ${_('Commit')}
118 % else:
119 <span>0</span> ${_('Commits')}
120 % endif
109 121 % else:
110 <a href="${h.route_path('repo_changelog', repo_name=c.repo_name)}">
111 ${_ungettext('%(num)s Commit', '%(num)s Commits', commit_rev) % {'num': commit_rev}}</a>
122 <a href="${h.route_path('repo_commits', repo_name=c.repo_name)}">
123 <i class="icon-history"></i>
124 % if commit_rev == 1:
125 <span>${commit_rev}</span> ${_('Commit')}
126 % else:
127 <span>${commit_rev}</span> ${_('Commits')}
128 % endif
129 </a>
112 130 % endif
113 131 </span>
114 132
115 133 ## forks
116 <span class="tag">
134 <span class="summary-tag">
117 135 <a title="${_('Number of Repository Forks')}" href="${h.route_path('repo_forks_show_all', repo_name=c.repo_name)}">
118 ${c.repository_forks} ${_ungettext('Fork', 'Forks', c.repository_forks)}</a>
136 <i class="icon-code-fork"></i>
137 <span>${c.repository_forks}</span> ${_ungettext('Fork', 'Forks', c.repository_forks)}</a>
119 138 </span>
139 </div>
140 </div>
141 </div>
142 </div>
143 ## owner, description, downloads, statistics
120 144
121 </div>
145 ## Owner
146 <div class="fieldset collapsable-content" data-toggle="summary-details" style="display: none;">
147 <div class="left-label-summary">
148 <p>${_('Owner')}</p>
149 <div class="right-label-summary">
150 ${base.gravatar_with_user(c.rhodecode_db_repo.user.email, 16)}
151 </div>
152
153 </div>
154 </div>
155
156 ## Description
157 <div class="fieldset collapsable-content" data-toggle="summary-details" style="display: none;">
158 <div class="left-label-summary">
159 <p>${_('Description')}</p>
160
161 <div class="right-label-summary input ${summary(c.show_stats)}">
162 <%namespace name="dt" file="/data_table/_dt_elements.mako"/>
163 ${dt.repo_desc(c.rhodecode_db_repo.description_safe, c.visual.stylify_metatags)}
122 164 </div>
123 165 </div>
124 166 </div>
125 167
168 ## Downloads
169 % if show_downloads:
170 <div class="fieldset collapsable-content" data-toggle="summary-details" style="display: none;">
171 <div class="left-label-summary">
172 <p>${_('Downloads')}</p>
173
174 <div class="right-label-summary input ${summary(c.show_stats)} downloads">
175 % if c.rhodecode_repo and len(c.rhodecode_repo.commit_ids) == 0:
176 <span class="disabled">
177 ${_('There are no downloads yet')}
178 </span>
179 % elif not c.enable_downloads:
180 <span class="disabled">
181 ${_('Downloads are disabled for this repository')}.
182 </span>
183 % if c.is_super_admin:
184 ${h.link_to(_('Enable downloads'),h.route_path('edit_repo',repo_name=c.repo_name, _anchor='repo_enable_downloads'))}
185 % endif
186 % else:
187 <span class="enabled">
188 <a id="archive_link" class="btn btn-small" href="${h.route_path('repo_archivefile',repo_name=c.rhodecode_db_repo.repo_name,fname='tip.zip')}">
189 <i class="icon-archive"></i> tip.zip
190 ## replaced by some JS on select
191 </a>
192 </span>
193 ${h.hidden('download_options')}
194 % endif
195 </div>
196 </div>
197 </div>
198 % endif
199
200 ## Repo size
126 201 <div class="fieldset collapsable-content" data-toggle="summary-details" style="display: none;">
127 202 <div class="left-label-summary">
128 ${_('Repository size')}:
129 </div>
130 <div class="right-content">
131 <div class="commit-info">
203 <p>${_('Repository size')}</p>
204
205 <div class="right-label-summary">
132 206 <div class="tags">
133 207 ## repo size
134 208 % if commit_rev == -1:
@@ -146,66 +220,21 b''
146 220 </div>
147 221 </div>
148 222
149 <div class="fieldset collapsable-content" data-toggle="summary-details" style="display: none;">
150 <div class="left-label-summary">
151 ${_('Description')}:
152 </div>
153 <div class="right-content">
154 <div class="input ${summary(c.show_stats)}">
155 <%namespace name="dt" file="/data_table/_dt_elements.mako"/>
156 ${dt.repo_desc(c.rhodecode_db_repo.description_safe, c.visual.stylify_metatags)}
157 </div>
158 </div>
159 </div>
160
161 % if show_downloads:
162 <div class="fieldset collapsable-content" data-toggle="summary-details" style="display: none;">
163 <div class="left-label-summary">
164 ${_('Downloads')}:
165 </div>
166 <div class="right-content">
167 <div class="input ${summary(c.show_stats)} downloads">
168 % if c.rhodecode_repo and len(c.rhodecode_repo.commit_ids) == 0:
169 <span class="disabled">
170 ${_('There are no downloads yet')}
171 </span>
172 % elif not c.enable_downloads:
173 <span class="disabled">
174 ${_('Downloads are disabled for this repository')}.
175 </span>
176 % if h.HasPermissionAll('hg.admin')('enable downloads on from summary'):
177 ${h.link_to(_('Enable downloads'),h.route_path('edit_repo',repo_name=c.repo_name, _anchor='repo_enable_downloads'))}
178 % endif
179 % else:
180 <span class="enabled">
181 <a id="archive_link" class="btn btn-small" href="${h.route_path('repo_archivefile',repo_name=c.rhodecode_db_repo.repo_name,fname='tip.zip')}">
182 <i class="icon-archive"></i> tip.zip
183 ## replaced by some JS on select
184 </a>
185 </span>
186 ${h.hidden('download_options')}
187 % endif
188 </div>
189 </div>
190 </div>
191 % endif
192
193 223 ## Statistics
194 224 <div class="fieldset collapsable-content" data-toggle="summary-details" style="display: none;">
195 225 <div class="left-label-summary">
196 ${_('Statistics')}:
197 </div>
198 <div class="right-content">
199 <div class="input ${summary(c.show_stats)} statistics">
226 <p>${_('Code Statistics')}</p>
227
228 <div class="right-label-summary input ${summary(c.show_stats)} statistics">
200 229 % if c.show_stats:
201 230 <div id="lang_stats" class="enabled">
202 ${_('Calculating Code Statistics...')}
231 <a href="#showSize" onclick="calculateSize(); $('#show-repo-size').hide(); $(this).hide(); return false" id="show-repo-size">Show code statistics</a>
203 232 </div>
204 233 % else:
205 234 <span class="disabled">
206 235 ${_('Statistics are disabled for this repository')}.
207 236 </span>
208 % if h.HasPermissionAll('hg.admin')('enable stats on from summary'):
237 % if c.is_super_admin:
209 238 ${h.link_to(_('Enable statistics'),h.route_path('edit_repo',repo_name=c.repo_name, _anchor='repo_enable_statistics'))}
210 239 % endif
211 240 % endif
@@ -214,18 +243,10 b''
214 243 </div>
215 244 </div>
216 245
246
217 247 </div><!--end summary-detail-->
218 </%def>
219 248
220 <%def name="summary_stats(gravatar_function)">
221 <div class="sidebar-right">
222 <div class="summary-detail-header">
223 <h4 class="item">
224 ${_('Owner')}
225 </h4>
226 </div>
227 <div class="sidebar-right-content">
228 ${gravatar_function(c.rhodecode_db_repo.user.email, 16)}
229 </div>
230 </div><!--end sidebar-right-->
249 <div id="summary_details_expand" class="btn-collapse" data-toggle="summary-details">
250 ${_('Show More')}
251 </div>
231 252 </%def>
@@ -3,13 +3,9 b''
3 3 <%namespace name="components" file="/summary/components.mako"/>
4 4
5 5 <%def name="main()">
6 <div class="title">
7 ${self.repo_page_title(c.rhodecode_db_repo)}
8 </div>
9 6
10 7 <div id="repo-summary" class="summary">
11 8 ${components.summary_detail(breadcrumbs_links=self.breadcrumbs_links(), show_downloads=False)}
12 ${components.summary_stats(gravatar_function=self.gravatar_with_user)}
13 9 </div><!--end repo-summary-->
14 10
15 11 <div class="alert alert-dismissable alert-warning">
@@ -9,47 +9,35 b''
9 9
10 10 <%def name="main()">
11 11
12 <div class="title">
13 ${self.repo_page_title(c.rhodecode_db_repo)}
14 ## Context Action
15 <div>
16 <ul class="links icon-only-links block-right">
17 <li>
18 %if c.rhodecode_user.username != h.DEFAULT_USER:
19 <a href="${h.route_path('atom_feed_home', repo_name=c.rhodecode_db_repo.repo_name, _query=dict(auth_token=c.rhodecode_user.feed_token))}" title="${_('RSS Feed')}" class="btn btn-sm"><i class="icon-rss-sign"></i>RSS</a>
20 %else:
21 <a href="${h.route_path('atom_feed_home', repo_name=c.rhodecode_db_repo.repo_name)}" title="${_('RSS Feed')}" class="btn btn-sm"><i class="icon-rss-sign"></i>RSS</a>
22 %endif
23 </li>
24 </ul>
25 </div>
26 </div>
27
28 12 <div id="repo-summary" class="summary">
29 13 ${components.summary_detail(breadcrumbs_links=self.breadcrumbs_links(), show_downloads=True)}
30 ${components.summary_stats(gravatar_function=self.gravatar_with_user)}
31 14 </div><!--end repo-summary-->
32 15
33 16
34 <div class="box" >
35 %if not c.repo_commits:
36 <div class="title">
37 <h3>${_('Quick start')}</h3>
17 <div class="box">
18 %if not c.repo_commits:
19 <div class="empty-repo">
20 <div class="title">
21 <h3>${_('Quick start')}</h3>
22 </div>
23 <div class="clear-fix"></div>
24 </div>
25 %endif
26 <div class="table">
27 <div id="shortlog_data">
28 <%include file='summary_commits.mako'/>
29 </div>
38 30 </div>
39 %endif
40 <div class="table">
41 <div id="shortlog_data">
42 <%include file='summary_commits.mako'/>
43 </div>
44 </div>
45 31 </div>
46 32
47 33 %if c.readme_data:
48 34 <div id="readme" class="anchor">
49 <div class="box" >
35 <div class="box">
50 36 <div class="title" title="${h.tooltip(_('Readme file from commit %s:%s') % (c.rhodecode_db_repo.landing_rev[0], c.rhodecode_db_repo.landing_rev[1]))}">
51 37 <h3 class="breadcrumbs">
52 <a href="${h.route_path('repo_files',repo_name=c.repo_name,commit_id=c.rhodecode_db_repo.landing_rev[1],f_path=c.readme_file)}">${c.readme_file}</a>
38 <a href="${h.route_path('repo_files',repo_name=c.repo_name,commit_id=c.rhodecode_db_repo.landing_rev[1],f_path=c.readme_file)}">
39 ${c.readme_file}
40 </a>
53 41 </h3>
54 42 </div>
55 43 <div class="readme codeblock">
@@ -20,8 +20,7 b''
20 20 </%def>
21 21
22 22
23 <%def name="breadcrumbs_links()">
24 </%def>
23 <%def name="breadcrumbs_links()"></%def>
25 24
26 25
27 26 <%def name="main()">
@@ -4,12 +4,12 b''
4 4 <table class="rctable repo_summary table_disp">
5 5 <tr>
6 6
7 <th class="status" colspan="2"></th>
7 <th class="status"></th>
8 8 <th>${_('Commit')}</th>
9 9 <th>${_('Commit message')}</th>
10 10 <th>${_('Age')}</th>
11 11 <th>${_('Author')}</th>
12 <th>${_('Refs')}</th>
12 <th colspan="2">${_('Refs')}</th>
13 13 </tr>
14 14
15 15 ## to speed up lookups cache some functions before the loop
@@ -37,13 +37,6 b''
37 37 <div class="tooltip flag_status not_reviewed" title="${_('Commit status: Not Reviewed')}"></div>
38 38 %endif
39 39 </td>
40 <td class="td-comments">
41 %if c.comments.get(cs.raw_id,[]):
42 <a title="${_('Commit has comments')}" href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=cs.raw_id,_anchor='comment-%s' % c.comments[cs.raw_id][0].comment_id)}">
43 <i class="icon-comment"></i> ${len(c.comments[cs.raw_id])}
44 </a>
45 %endif
46 </td>
47 40 <td class="td-commit">
48 41 <code>
49 42 <a href="${h.route_path('repo_commit', repo_name=c.repo_name, commit_id=cs.raw_id)}">${h.show_id(cs)}</a>
@@ -83,19 +76,34 b''
83 76 ## branch
84 77 %if cs.branch:
85 78 <span class="branchtag tag" title="${h.tooltip(_('Branch %s') % cs.branch)}">
86 <a href="${h.route_path('repo_changelog',repo_name=c.repo_name,_query=dict(branch=cs.branch))}"><i class="icon-code-fork"></i>${h.shorter(cs.branch)}</a>
79 <a href="${h.route_path('repo_commits',repo_name=c.repo_name,_query=dict(branch=cs.branch))}"><i class="icon-code-fork"></i>${h.shorter(cs.branch)}</a>
87 80 </span>
88 81 %endif
89 82 </div>
90 83 </td>
84 <td class="td-comments">
85 <% cs_comments = c.comments.get(cs.raw_id,[]) %>
86 % if cs_comments:
87 <a title="${_('Commit has comments')}" href="${h.route_path('repo_commit',repo_name=c.repo_name,commit_id=cs.raw_id,_anchor='comment-%s' % cs_comments[0].comment_id)}">
88 <i class="icon-comment"></i> ${len(cs_comments)}
89 </a>
90 % else:
91 <i class="icon-comment"></i> ${len(cs_comments)}
92 % endif
93 </td>
91 94 </tr>
92 95 %endfor
93 96
94 97 </table>
95 98
96 99 <script type="text/javascript">
97 $(document).pjax('#shortlog_data .pager_link','#shortlog_data', {timeout: 2000, scrollTo: false, push: false});
100 $(document).pjax('#shortlog_data .pager_link','#shortlog_data', {timeout: 5000, scrollTo: false, push: false});
98 101 $(document).on('pjax:success', function(){ timeagoActivate(); });
102 $(document).on('pjax:timeout', function(event) {
103 // Prevent default timeout redirection behavior
104 event.preventDefault()
105 })
106
99 107 </script>
100 108
101 109 <div class="pagination-wh pagination-left">
@@ -106,40 +114,54 b''
106 114 %if h.HasRepoPermissionAny('repository.write','repository.admin')(c.repo_name):
107 115 <div class="quick_start">
108 116 <div class="fieldset">
109 <div class="left-label">${_('Add or upload files directly via RhodeCode:')}</div>
110 <div class="right-content">
111 <div id="add_node_id" class="add_node">
112 <a href="${h.route_path('repo_files_add_file',repo_name=c.repo_name,commit_id=0, f_path='', _anchor='edit')}" class="btn btn-default">${_('Add New File')}</a>
113 </div>
117 <p><b>${_('Add or upload files directly via RhodeCode:')}</b></p>
118 <div class="pull-left">
119 <a href="${h.route_path('repo_files_add_file',repo_name=c.repo_name,commit_id=0, f_path='')}" class="btn btn-default">${_('Add New File')}</a>
120 </div>
121 <div class="pull-left">
122 <a href="${h.route_path('repo_files_upload_file',repo_name=c.repo_name,commit_id=0, f_path='')}" class="btn btn-default">${_('Upload New File')}</a>
114 123 </div>
115 124 %endif
116 125 </div>
117 126
118 %if not h.is_svn(c.rhodecode_repo):
119 <div class="fieldset">
120 <div class="left-label">${_('Push new repo:')}</div>
121 <div class="right-content">
122 <pre>
123 ${c.rhodecode_repo.alias} clone ${c.clone_repo_url}
124 ${c.rhodecode_repo.alias} add README # add first file
125 ${c.rhodecode_repo.alias} commit -m "Initial" # commit with message
126 ${c.rhodecode_repo.alias} push ${'origin master' if h.is_git(c.rhodecode_repo) else ''} # push changes back
127 </pre>
128 </div>
129 </div>
130 <div class="fieldset">
131 <div class="left-label">${_('Existing repository?')}</div>
132 <div class="right-content">
133 <pre>
134 %if h.is_git(c.rhodecode_repo):
127 <div class="fieldset">
128 <p><b>${_('Push new repo:')}</b></p>
129 <pre>
130 %if h.is_git(c.rhodecode_repo):
131 git clone ${c.clone_repo_url}
132 git add README # add first file
133 git commit -m "Initial commit" # commit with message
134 git remote add origin ${c.clone_repo_url}
135 git push -u origin master # push changes back to default master branch
136 %elif h.is_hg(c.rhodecode_repo):
137 hg clone ${c.clone_repo_url}
138 hg add README # add first file
139 hg commit -m "Initial commit" # commit with message
140 hg push ${c.clone_repo_url}
141 %elif h.is_svn(c.rhodecode_repo):
142 svn co ${c.clone_repo_url}
143 svn add README # add first file
144 svn commit -m "Initial commit"
145 svn commit # send changes back to the server
146 %endif
147 </pre>
148 </div>
149
150 <div class="fieldset">
151 <p><b>${_('Existing repository?')}</b></p>
152 <pre>
153 %if h.is_git(c.rhodecode_repo):
135 154 git remote add origin ${c.clone_repo_url}
136 155 git push -u origin master
137 %else:
156 %elif h.is_hg(c.rhodecode_repo):
138 157 hg push ${c.clone_repo_url}
139 %endif
140 </pre>
141 </div>
142 </div>
143 %endif
158 %elif h.is_svn(c.rhodecode_repo):
159 svn co ${c.clone_repo_url}
160 %endif
161 </pre>
162
163 </div>
164
165
144 166 </div>
145 167 %endif
@@ -8,10 +8,7 b''
8 8 %endif
9 9 </%def>
10 10
11 <%def name="breadcrumbs_links()">
12 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
13 <span id="obj_count">0</span> ${_('tags')}
14 </%def>
11 <%def name="breadcrumbs_links()"></%def>
15 12
16 13 <%def name="menu_bar_nav()">
17 14 ${self.menu_items(active='repositories')}
@@ -24,7 +21,7 b''
24 21 <%def name="main()">
25 22 <div class="box">
26 23 <div class="title">
27 ${self.repo_page_title(c.rhodecode_db_repo)}
24
28 25 %if c.has_references:
29 26 <ul class="links">
30 27 <li>
@@ -33,7 +30,8 b''
33 30 </ul>
34 31 %endif
35 32 %if c.has_references:
36 ${self.breadcrumbs()}
33 <input class="q_filter_box" id="q_filter" size="15" type="text" name="filter" placeholder="${_('quick filter...')}" value=""/>
34 <span id="obj_count">0</span> ${_('tags')}
37 35 %endif
38 36 </div>
39 37 <table id="obj_list_table" class="display"></table>
@@ -3,23 +3,24 b''
3 3 <div class="panel panel-default user-profile">
4 4 <div class="panel-heading">
5 5 <h3 class="panel-title">${_('User group profile')}</h3>
6 %if h.HasPermissionAny('hg.admin')():
6 %if c.is_super_admin:
7 7 ${h.link_to(_('Edit'), h.route_path('edit_user_group', user_group_id=c.user_group.users_group_id), class_='panel-edit')}
8 8 %endif
9 9 </div>
10 10
11 <div class="panel-body user-profile-content">
12
13 <div class="fieldset">
14 <div class="left-label">
11 <div class="panel-body user-profile-content fields">
12 <div class="field">
13 <div class="label">
15 14 ${_('Group Name')}:
16 15 </div>
17 <div class="right-content">
16 <div class="input">
17 <div class="text-as-placeholder">
18 18 ${c.user_group.users_group_name}
19 </div>
19 20 </div>
20 21 </div>
21 <div class="fieldset">
22 <div class="left-label">
22 <div class="field">
23 <div class="label">
23 24 ${_('Owner')}:
24 25 </div>
25 26 <div class="group_member">
@@ -28,20 +29,24 b''
28 29
29 30 </div>
30 31 </div>
31 <div class="fieldset">
32 <div class="left-label">
32 <div class="field">
33 <div class="label">
33 34 ${_('Active')}:
34 35 </div>
35 <div class="right-content">
36 <div class="input">
37 <div class="text-as-placeholder">
36 38 ${c.user_group.users_group_active}
39 </div>
37 40 </div>
38 41 </div>
39 42 % if not c.anonymous:
40 <div class="fieldset">
41 <div class="left-label">
43 <div class="field">
44 <div class="label">
42 45 ${_('Members')}:
43 46 </div>
44 <div class="right-content">
47
48 <div class="input">
49 <div class="text-as-placeholder">
45 50 <table id="group_members_placeholder" class="rctable group_members">
46 51 <th>${_('Username')}</th>
47 52 % if c.group_members:
@@ -65,6 +70,7 b''
65 70 </table>
66 71 </div>
67 72 </div>
73 </div>
68 74 % endif
69 75 </div>
70 76 </div> No newline at end of file
@@ -3,55 +3,64 b''
3 3 <div class="panel panel-default user-profile">
4 4 <div class="panel-heading">
5 5 <h3 class="panel-title">${_('User Profile')}</h3>
6 %if h.HasPermissionAny('hg.admin')():
6 %if c.is_super_admin:
7 7 ${h.link_to(_('Edit'), h.route_path('user_edit', user_id=c.user.user_id), class_='panel-edit')}
8 8 %endif
9 9 </div>
10 10
11 <div class="panel-body user-profile-content">
12 <div class="fieldset">
13 <div class="left-label">
11 <div class="panel-body user-profile-content fields">
12 <div class="field">
13 <div class="label">
14 14 ${_('Photo')}:
15 15 </div>
16 <div class="right-content">
16 <div class="input">
17 <div class="text-as-placeholder">
17 18 %if c.visual.use_gravatar:
18 19 ${base.gravatar(c.user.email, 100)}
19 20 %else:
20 ${base.gravatar(c.user.email, 20)}
21 ${_('Avatars are disabled')}
21 ${base.gravatar(c.user.email, 100)}
22 22 %endif
23 </div>
23 24 </div>
24 25 </div>
25 <div class="fieldset">
26 <div class="left-label">
26 <div class="field">
27 <div class="label">
27 28 ${_('Username')}:
28 29 </div>
29 <div class="right-content">
30 ${c.user.username}
30 <div class="input">
31 <div class="text-as-placeholder">
32 ${c.user.username}
33 </div>
31 34 </div>
32 35 </div>
33 <div class="fieldset">
34 <div class="left-label">
36 <div class="field">
37 <div class="label">
35 38 ${_('First name')}:
36 39 </div>
37 <div class="right-content">
38 ${c.user.first_name}
40 <div class="input">
41 <div class="text-as-placeholder">
42 ${c.user.first_name}
43 </div>
39 44 </div>
40 45 </div>
41 <div class="fieldset">
42 <div class="left-label">
46 <div class="field">
47 <div class="label">
43 48 ${_('Last name')}:
44 49 </div>
45 <div class="right-content">
46 ${c.user.last_name}
50 <div class="input">
51 <div class="text-as-placeholder">
52 ${c.user.last_name}
53 </div>
47 54 </div>
48 55 </div>
49 <div class="fieldset">
50 <div class="left-label">
56 <div class="field">
57 <div class="label">
51 58 ${_('Email')}:
52 59 </div>
53 <div class="right-content">
54 ${c.user.email or _('Missing email, please update your user email address.')}
60 <div class="input">
61 <div class="text-as-placeholder">
62 ${(c.user.email or _('Missing email, please update your user email address.'))}
63 </div>
55 64 </div>
56 65 </div>
57 66 </div>
@@ -1,1 +1,1 b''
1 {"results": [{"text": "Changesets", "children": [{"text": "r625:ead8f28a4bc2", "id": "ead8f28a4bc2f45ecfb148a6b8a89758b9654a84"}, {"text": "r535:c093f94d6d35", "id": "c093f94d6d358f13c55a687da66c30c41cca4153"}, {"text": "r534:559f640ec08b", "id": "559f640ec08b2a14c4a9ac863d8ca273545b8885"}, {"text": "r490:02a940b4ee37", "id": "02a940b4ee371ec64ef5b4c4870a5c89dc7fb98a"}, {"text": "r464:b45a4153a2d7", "id": "b45a4153a2d7adb8a78b63d35d39fac44a4320a6"}, {"text": "r460:0a54e66b9450", "id": "0a54e66b94502409074b163cd93c1233dcc0413f"}, {"text": "r457:a7bf2f6bf3d5", "id": "a7bf2f6bf3d5273da4bcd2032a891acae5a45e2b"}, {"text": "r456:7266de0154b4", "id": "7266de0154b4da7c42ba3d788876056dbf116b5a"}, {"text": "r455:666de4ee6507", "id": "666de4ee65074cd3e37ea01e75f65bd3e4c336bb"}, {"text": "r453:91acc599141c", "id": "91acc599141c87f03e0e3551dcaacf4492632e58"}, {"text": "r442:40a2d5d71b75", "id": "40a2d5d71b758e7eafc84a324ed55142cba22f42"}, {"text": "r440:d1f898326327", "id": "d1f898326327e20524fe22417c22d71064fe54a1"}, {"text": "r420:162a36830c23", "id": "162a36830c23ccf1bf1873157fd0c8d0dfc7c817"}, {"text": "r345:c994f0de03b2", "id": "c994f0de03b2a0aa848a04fc2c0d7e737dba31fc"}, {"text": "r340:5d3d4d2c262e", "id": "5d3d4d2c262e17b247d405feceeb09ff7408c940"}, {"text": "r334:4d4278a6390e", "id": "4d4278a6390e42f4fc777ecf1b9b628e77da8e22"}, {"text": "r298:00dffb625166", "id": "00dffb62516650bc5050d818eb47ea1ca207954d"}, {"text": "r297:47b6be9a812e", "id": "47b6be9a812ec3ed0384001a458a759f0f583fe2"}, {"text": "r289:1589fed841cd", "id": "1589fed841cd9ef33155f8560727809ac3ada2c8"}, {"text": "r285:afafd0ee2821", "id": "afafd0ee28218ab979678213cb96e9e4dbd7359b"}, {"text": "r284:639b115ed2b0", "id": "639b115ed2b02017824005b5ae66282c6e25eba8"}, {"text": "r283:fcf7562d7305", "id": "fcf7562d7305affc94fe20dc89a34aefd2b8aa1e"}, {"text": "r256:ec8cbdb5f364", "id": "ec8cbdb5f364fce7843cbf148c3d95d86f935339"}, {"text": "r255:0d74d2e2bdf3", "id": "0d74d2e2bdf3dcd5ee9fe4fcfe9016c5c6486f35"}, {"text": "r243:6894ad7d8223", "id": "6894ad7d8223b1e6853e9fdaa2c38d3f0cef1e38"}, {"text": "r231:31b3f4b599fa", "id": "31b3f4b599fae5f12cf438c73403679cdf923d75"}, {"text": "r220:3d2515dd21fb", "id": "3d2515dd21fb34fe6c5d0029075a863f3e92f5f6"}, {"text": "r186:f804e27aa496", "id": "f804e27aa4961f2e327f2a10ee373235df20ee21"}, {"text": "r182:7f00513785a1", "id": "7f00513785a13f273a4387ef086bb795b37f013c"}, {"text": "r181:6efcdc61028c", "id": "6efcdc61028c8edd1c787b3439fae71b77a17357"}, {"text": "r175:6c0ce52b229a", "id": "6c0ce52b229aa978889e91b38777f800e85f330b"}, {"text": "r165:09788a0b8a54", "id": "09788a0b8a5455e9678c3959214246574e546d4f"}, {"text": "r163:0164ee729def", "id": "0164ee729def0a253d6dcb594b5ee2a52fef4748"}, {"text": "r140:33fa32233551", "id": "33fa3223355104431402a888fa77a4e9956feb3e"}, {"text": "r126:fa014c12c26d", "id": "fa014c12c26d10ba682fadb78f2a11c24c8118e1"}, {"text": "r111:e686b958768e", "id": "e686b958768ee96af8029fe19c6050b1a8dd3b2b"}, {"text": "r109:ab5721ca0a08", "id": "ab5721ca0a081f26bf43d9051e615af2cc99952f"}, {"text": "r108:c877b68d18e7", "id": "c877b68d18e792a66b7f4c529ea02c8f80801542"}, {"text": "r107:4313566d2e41", "id": "4313566d2e417cb382948f8d9d7c765330356054"}, {"text": "r104:6c2303a79367", "id": "6c2303a793671e807d1cfc70134c9ca0767d98c2"}, {"text": "r102:54386793436c", "id": "54386793436c938cff89326944d4c2702340037d"}, {"text": "r101:54000345d2e7", "id": "54000345d2e78b03a99d561399e8e548de3f3203"}, {"text": "r99:1c6b3677b37e", "id": "1c6b3677b37ea064cb4b51714d8f7498f93f4b2b"}, {"text": "r93:2d03ca750a44", "id": "2d03ca750a44440fb5ea8b751176d1f36f8e8f46"}, {"text": "r92:2a08b128c206", "id": "2a08b128c206db48c2f0b8f70df060e6db0ae4f8"}, {"text": "r91:30c26513ff1e", "id": "30c26513ff1eb8e5ce0e1c6b477ee5dc50e2f34b"}, {"text": "r82:ac71e9503c2c", "id": "ac71e9503c2ca95542839af0ce7b64011b72ea7c"}, {"text": "r81:12669288fd13", "id": "12669288fd13adba2a9b7dd5b870cc23ffab92d2"}, {"text": "r76:5a0c84f3e6fe", "id": "5a0c84f3e6fe3473e4c8427199d5a6fc71a9b382"}, {"text": "r73:12f2f5e2b38e", "id": "12f2f5e2b38e6ff3fbdb5d722efed9aa72ecb0d5"}, {"text": "r61:5eab1222a7cd", "id": "5eab1222a7cd4bfcbabc218ca6d04276d4e27378"}, {"text": "r60:f50f42baeed5", "id": "f50f42baeed5af6518ef4b0cb2f1423f3851a941"}, {"text": "r59:d7e390a45f6a", "id": "d7e390a45f6aa96f04f5e7f583ad4f867431aa25"}, {"text": "r58:f15c21f97864", "id": "f15c21f97864b4f071cddfbf2750ec2e23859414"}, {"text": "r57:e906ef056cf5", "id": "e906ef056cf539a4e4e5fc8003eaf7cf14dd8ade"}, {"text": "r56:ea2b108b48aa", "id": "ea2b108b48aa8f8c9c4a941f66c1a03315ca1c3b"}, {"text": "r50:84dec09632a4", "id": "84dec09632a4458f79f50ddbbd155506c460b4f9"}, {"text": "r48:0115510b70c7", "id": "0115510b70c7229dbc5dc49036b32e7d91d23acd"}, {"text": "r46:2a13f185e452", "id": "2a13f185e4525f9d4b59882791a2d397b90d5ddc"}, {"text": "r30:3bf1c5868e57", "id": "3bf1c5868e570e39569d094f922d33ced2fa3b2b"}, {"text": "r26:b8d040125747", "id": "b8d04012574729d2c29886e53b1a43ef16dd00a1"}, {"text": "r24:6970b057cffe", "id": "6970b057cffe4aab0a792aa634c89f4bebf01441"}, {"text": "r8:dd80b0f6cf50", "id": "dd80b0f6cf5052f17cc738c2951c4f2070200d7f"}, {"text": "r7:ff7ca51e58c5", "id": "ff7ca51e58c505fec0dd2491de52c622bb7a806b"}]}, {"text": "Branches", "children": [{"text": "master", "id": "fd627b9e0dd80b47be81af07c4a98518244ed2f7"}]}, {"text": "Tags", "children": [{"text": "v0.2.2", "id": "137fea89f304a42321d40488091ee2ed419a3686"}, {"text": "v0.2.1", "id": "5051d0fa344d4408a2659d9a0348eb2d41868ecf"}, {"text": "v0.2.0", "id": "599ba911aa24d2981225f3966eb659dfae9e9f30"}, {"text": "v0.1.9", "id": "341d28f0eec5ddf0b6b77871e13c2bbd6bec685c"}, {"text": "v0.1.8", "id": "74ebce002c088b8a5ecf40073db09375515ecd68"}, {"text": "v0.1.7", "id": "4d78bf73b5c22c82b68f902f138f7881b4fffa2c"}, {"text": "v0.1.6", "id": "0205cb3f44223fb3099d12a77a69c81b798772d9"}, {"text": "v0.1.5", "id": "6c0ce52b229aa978889e91b38777f800e85f330b"}, {"text": "v0.1.4", "id": "7d735150934cd7645ac3051903add952390324a5"}, {"text": "v0.1.3", "id": "5a3a8fb005554692b16e21dee62bf02667d8dc3e"}, {"text": "v0.1.2", "id": "0ba5f8a4660034ff25c0cac2a5baabf5d2791d63"}, {"text": "v0.1.11", "id": "c60f01b77c42dce653d6b1d3b04689862c261929"}, {"text": "v0.1.10", "id": "10cddef6b794696066fb346434014f0a56810218"}, {"text": "v0.1.1", "id": "e6ea6d16e2f26250124a1f4b4fe37a912f9d86a0"}]}], "more": false}
1 {"results": [{"text": "Changesets", "children": [{"text": "r625:ead8f28a4bc2", "type": "sha", "id": "ead8f28a4bc2f45ecfb148a6b8a89758b9654a84"}, {"text": "r535:c093f94d6d35", "type": "sha", "id": "c093f94d6d358f13c55a687da66c30c41cca4153"}, {"text": "r534:559f640ec08b", "type": "sha", "id": "559f640ec08b2a14c4a9ac863d8ca273545b8885"}, {"text": "r490:02a940b4ee37", "type": "sha", "id": "02a940b4ee371ec64ef5b4c4870a5c89dc7fb98a"}, {"text": "r464:b45a4153a2d7", "type": "sha", "id": "b45a4153a2d7adb8a78b63d35d39fac44a4320a6"}, {"text": "r460:0a54e66b9450", "type": "sha", "id": "0a54e66b94502409074b163cd93c1233dcc0413f"}, {"text": "r457:a7bf2f6bf3d5", "type": "sha", "id": "a7bf2f6bf3d5273da4bcd2032a891acae5a45e2b"}, {"text": "r456:7266de0154b4", "type": "sha", "id": "7266de0154b4da7c42ba3d788876056dbf116b5a"}, {"text": "r455:666de4ee6507", "type": "sha", "id": "666de4ee65074cd3e37ea01e75f65bd3e4c336bb"}, {"text": "r453:91acc599141c", "type": "sha", "id": "91acc599141c87f03e0e3551dcaacf4492632e58"}, {"text": "r442:40a2d5d71b75", "type": "sha", "id": "40a2d5d71b758e7eafc84a324ed55142cba22f42"}, {"text": "r440:d1f898326327", "type": "sha", "id": "d1f898326327e20524fe22417c22d71064fe54a1"}, {"text": "r420:162a36830c23", "type": "sha", "id": "162a36830c23ccf1bf1873157fd0c8d0dfc7c817"}, {"text": "r345:c994f0de03b2", "type": "sha", "id": "c994f0de03b2a0aa848a04fc2c0d7e737dba31fc"}, {"text": "r340:5d3d4d2c262e", "type": "sha", "id": "5d3d4d2c262e17b247d405feceeb09ff7408c940"}, {"text": "r334:4d4278a6390e", "type": "sha", "id": "4d4278a6390e42f4fc777ecf1b9b628e77da8e22"}, {"text": "r298:00dffb625166", "type": "sha", "id": "00dffb62516650bc5050d818eb47ea1ca207954d"}, {"text": "r297:47b6be9a812e", "type": "sha", "id": "47b6be9a812ec3ed0384001a458a759f0f583fe2"}, {"text": "r289:1589fed841cd", "type": "sha", "id": "1589fed841cd9ef33155f8560727809ac3ada2c8"}, {"text": "r285:afafd0ee2821", "type": "sha", "id": "afafd0ee28218ab979678213cb96e9e4dbd7359b"}, {"text": "r284:639b115ed2b0", "type": "sha", "id": "639b115ed2b02017824005b5ae66282c6e25eba8"}, {"text": "r283:fcf7562d7305", "type": "sha", "id": "fcf7562d7305affc94fe20dc89a34aefd2b8aa1e"}, {"text": "r256:ec8cbdb5f364", "type": "sha", "id": "ec8cbdb5f364fce7843cbf148c3d95d86f935339"}, {"text": "r255:0d74d2e2bdf3", "type": "sha", "id": "0d74d2e2bdf3dcd5ee9fe4fcfe9016c5c6486f35"}, {"text": "r243:6894ad7d8223", "type": "sha", "id": "6894ad7d8223b1e6853e9fdaa2c38d3f0cef1e38"}, {"text": "r231:31b3f4b599fa", "type": "sha", "id": "31b3f4b599fae5f12cf438c73403679cdf923d75"}, {"text": "r220:3d2515dd21fb", "type": "sha", "id": "3d2515dd21fb34fe6c5d0029075a863f3e92f5f6"}, {"text": "r186:f804e27aa496", "type": "sha", "id": "f804e27aa4961f2e327f2a10ee373235df20ee21"}, {"text": "r182:7f00513785a1", "type": "sha", "id": "7f00513785a13f273a4387ef086bb795b37f013c"}, {"text": "r181:6efcdc61028c", "type": "sha", "id": "6efcdc61028c8edd1c787b3439fae71b77a17357"}, {"text": "r175:6c0ce52b229a", "type": "sha", "id": "6c0ce52b229aa978889e91b38777f800e85f330b"}, {"text": "r165:09788a0b8a54", "type": "sha", "id": "09788a0b8a5455e9678c3959214246574e546d4f"}, {"text": "r163:0164ee729def", "type": "sha", "id": "0164ee729def0a253d6dcb594b5ee2a52fef4748"}, {"text": "r140:33fa32233551", "type": "sha", "id": "33fa3223355104431402a888fa77a4e9956feb3e"}, {"text": "r126:fa014c12c26d", "type": "sha", "id": "fa014c12c26d10ba682fadb78f2a11c24c8118e1"}, {"text": "r111:e686b958768e", "type": "sha", "id": "e686b958768ee96af8029fe19c6050b1a8dd3b2b"}, {"text": "r109:ab5721ca0a08", "type": "sha", "id": "ab5721ca0a081f26bf43d9051e615af2cc99952f"}, {"text": "r108:c877b68d18e7", "type": "sha", "id": "c877b68d18e792a66b7f4c529ea02c8f80801542"}, {"text": "r107:4313566d2e41", "type": "sha", "id": "4313566d2e417cb382948f8d9d7c765330356054"}, {"text": "r104:6c2303a79367", "type": "sha", "id": "6c2303a793671e807d1cfc70134c9ca0767d98c2"}, {"text": "r102:54386793436c", "type": "sha", "id": "54386793436c938cff89326944d4c2702340037d"}, {"text": "r101:54000345d2e7", "type": "sha", "id": "54000345d2e78b03a99d561399e8e548de3f3203"}, {"text": "r99:1c6b3677b37e", "type": "sha", "id": "1c6b3677b37ea064cb4b51714d8f7498f93f4b2b"}, {"text": "r93:2d03ca750a44", "type": "sha", "id": "2d03ca750a44440fb5ea8b751176d1f36f8e8f46"}, {"text": "r92:2a08b128c206", "type": "sha", "id": "2a08b128c206db48c2f0b8f70df060e6db0ae4f8"}, {"text": "r91:30c26513ff1e", "type": "sha", "id": "30c26513ff1eb8e5ce0e1c6b477ee5dc50e2f34b"}, {"text": "r82:ac71e9503c2c", "type": "sha", "id": "ac71e9503c2ca95542839af0ce7b64011b72ea7c"}, {"text": "r81:12669288fd13", "type": "sha", "id": "12669288fd13adba2a9b7dd5b870cc23ffab92d2"}, {"text": "r76:5a0c84f3e6fe", "type": "sha", "id": "5a0c84f3e6fe3473e4c8427199d5a6fc71a9b382"}, {"text": "r73:12f2f5e2b38e", "type": "sha", "id": "12f2f5e2b38e6ff3fbdb5d722efed9aa72ecb0d5"}, {"text": "r61:5eab1222a7cd", "type": "sha", "id": "5eab1222a7cd4bfcbabc218ca6d04276d4e27378"}, {"text": "r60:f50f42baeed5", "type": "sha", "id": "f50f42baeed5af6518ef4b0cb2f1423f3851a941"}, {"text": "r59:d7e390a45f6a", "type": "sha", "id": "d7e390a45f6aa96f04f5e7f583ad4f867431aa25"}, {"text": "r58:f15c21f97864", "type": "sha", "id": "f15c21f97864b4f071cddfbf2750ec2e23859414"}, {"text": "r57:e906ef056cf5", "type": "sha", "id": "e906ef056cf539a4e4e5fc8003eaf7cf14dd8ade"}, {"text": "r56:ea2b108b48aa", "type": "sha", "id": "ea2b108b48aa8f8c9c4a941f66c1a03315ca1c3b"}, {"text": "r50:84dec09632a4", "type": "sha", "id": "84dec09632a4458f79f50ddbbd155506c460b4f9"}, {"text": "r48:0115510b70c7", "type": "sha", "id": "0115510b70c7229dbc5dc49036b32e7d91d23acd"}, {"text": "r46:2a13f185e452", "type": "sha", "id": "2a13f185e4525f9d4b59882791a2d397b90d5ddc"}, {"text": "r30:3bf1c5868e57", "type": "sha", "id": "3bf1c5868e570e39569d094f922d33ced2fa3b2b"}, {"text": "r26:b8d040125747", "type": "sha", "id": "b8d04012574729d2c29886e53b1a43ef16dd00a1"}, {"text": "r24:6970b057cffe", "type": "sha", "id": "6970b057cffe4aab0a792aa634c89f4bebf01441"}, {"text": "r8:dd80b0f6cf50", "type": "sha", "id": "dd80b0f6cf5052f17cc738c2951c4f2070200d7f"}, {"text": "r7:ff7ca51e58c5", "type": "sha", "id": "ff7ca51e58c505fec0dd2491de52c622bb7a806b"}]}, {"text": "Branches", "children": [{"text": "master", "type": "branch", "id": "fd627b9e0dd80b47be81af07c4a98518244ed2f7"}]}, {"text": "Tags", "children": [{"text": "v0.2.2", "type": "tag", "id": "137fea89f304a42321d40488091ee2ed419a3686"}, {"text": "v0.2.1", "type": "tag", "id": "5051d0fa344d4408a2659d9a0348eb2d41868ecf"}, {"text": "v0.2.0", "type": "tag", "id": "599ba911aa24d2981225f3966eb659dfae9e9f30"}, {"text": "v0.1.9", "type": "tag", "id": "341d28f0eec5ddf0b6b77871e13c2bbd6bec685c"}, {"text": "v0.1.8", "type": "tag", "id": "74ebce002c088b8a5ecf40073db09375515ecd68"}, {"text": "v0.1.7", "type": "tag", "id": "4d78bf73b5c22c82b68f902f138f7881b4fffa2c"}, {"text": "v0.1.6", "type": "tag", "id": "0205cb3f44223fb3099d12a77a69c81b798772d9"}, {"text": "v0.1.5", "type": "tag", "id": "6c0ce52b229aa978889e91b38777f800e85f330b"}, {"text": "v0.1.4", "type": "tag", "id": "7d735150934cd7645ac3051903add952390324a5"}, {"text": "v0.1.3", "type": "tag", "id": "5a3a8fb005554692b16e21dee62bf02667d8dc3e"}, {"text": "v0.1.2", "type": "tag", "id": "0ba5f8a4660034ff25c0cac2a5baabf5d2791d63"}, {"text": "v0.1.11", "type": "tag", "id": "c60f01b77c42dce653d6b1d3b04689862c261929"}, {"text": "v0.1.10", "type": "tag", "id": "10cddef6b794696066fb346434014f0a56810218"}, {"text": "v0.1.1", "type": "tag", "id": "e6ea6d16e2f26250124a1f4b4fe37a912f9d86a0"}]}], "more": false}
@@ -1,1 +1,1 b''
1 {"results": [{"text": "Changesets", "children": [{"text": "r648:dbec37a0d5ca (default)", "id": "dbec37a0d5cab8ff39af4cfc4a4cd3996e4acfc6"}, {"text": "r639:1d20ed9eda94 (default)", "id": "1d20ed9eda9482d46ff0a6af5812550218b3ff15"}, {"text": "r547:0173395e8227 (default)", "id": "0173395e822797f098799ed95c1a81b6a547a9ad"}, {"text": "r546:afbb45ade933 (default)", "id": "afbb45ade933a8182f1d8ec5d4d1bb2de2572043"}, {"text": "r502:6f093e30cac3 (default)", "id": "6f093e30cac34e6b4b11275a9f22f80c5d7ad1f7"}, {"text": "r476:c7e2212dd2ae (default)", "id": "c7e2212dd2ae975d1d06534a3d7e317165c06960"}, {"text": "r472:45477506df79 (default)", "id": "45477506df79f701bf69419aac3e1f0fed3c5bcf"}, {"text": "r469:5fc76cb25d11 (default)", "id": "5fc76cb25d11e07c60de040f78b8cd265ff10d53"}, {"text": "r468:b073433cf899 (default)", "id": "b073433cf8994969ee5cd7cce84cbe587bb880b2"}, {"text": "r467:7a74dbfcacd1 (default)", "id": "7a74dbfcacd1dbcb58bb9c860b2f29fbb22c4c96"}, {"text": "r465:71ee52cc4d62 (default)", "id": "71ee52cc4d629096bdbee036325975dac2af4501"}, {"text": "r452:a5b217d26c5f (default)", "id": "a5b217d26c5f111e72bae4de672b084ee0fbf75c"}, {"text": "r450:47aedd538bf6 (default)", "id": "47aedd538bf616eedcb0e7d630ea476df0e159c7"}, {"text": "r432:8e4915fa32d7 (default)", "id": "8e4915fa32d727dcbf09746f637a5f82e539511e"}, {"text": "r356:25213a5fbb04 (default)", "id": "25213a5fbb048dff8ba65d21e466a835536e5b70"}, {"text": "r351:23debcedddc1 (default)", "id": "23debcedddc1c23c14be33e713e7786d4a9de471"}, {"text": "r342:61e25b2a90a1 (default)", "id": "61e25b2a90a19e7fffd75dea1e4c7e20df526bbe"}, {"text": "r318:fb95b340e0d0 (webvcs)", "id": "fb95b340e0d03fa51f33c56c991c08077c99303e"}, {"text": "r303:bda35e0e564f (default)", "id": "bda35e0e564fbbc5cd26fe0a37fb647a254c99fe"}, {"text": "r302:97ff74896d7d (default)", "id": "97ff74896d7dbf3115a337a421d44b55154acc89"}, {"text": "r293:cec3473c3fdb (default)", "id": "cec3473c3fdb9599c98067182a075b49bde570f9"}, {"text": "r289:0e86c43eef86 (default)", "id": "0e86c43eef866a013a587666a877c879899599bb"}, {"text": "r288:91a27c312808 (default)", "id": "91a27c312808100cf20a602f78befbbff9d89bfd"}, {"text": "r287:400e36a1670a (default)", "id": "400e36a1670a57d11e3edcb5b07bf82c30006d0b"}, {"text": "r261:014fb17dfc95 (default)", "id": "014fb17dfc95b0995e838c565376bf9a993e230a"}, {"text": "r260:cca7aebbc4d6 (default)", "id": "cca7aebbc4d6125798446b11e69dc8847834a982"}, {"text": "r258:14cdb2957c01 (workdir)", "id": "14cdb2957c011a5feba36f50d960d9832ba0f0c1"}, {"text": "r245:34df20118ed7 (default)", "id": "34df20118ed74b5987d22a579e8a60e903da5bf8"}, {"text": "r233:0375d9042a64 (workdir)", "id": "0375d9042a64a1ac1641528f0f0668f9a339e86d"}, {"text": "r222:94aa45fc1806 (workdir)", "id": "94aa45fc1806c04d4ba640933edf682c22478453"}, {"text": "r188:7ed99bc73881 (default)", "id": "7ed99bc738818879941e3ce20243f8856a7cfc84"}, {"text": "r184:1e85975528bc (default)", "id": "1e85975528bcebe853732a9e5fb8dbf4461f6bb2"}, {"text": "r183:ed30beddde7b (default)", "id": "ed30beddde7bbddb26042625be19bcd11576c1dd"}, {"text": "r177:a6664e18181c (default)", "id": "a6664e18181c6fc81b751a8d01474e7e1a3fe7fc"}, {"text": "r167:8911406ad776 (default)", "id": "8911406ad776fdd3d0b9932a2e89677e57405a48"}, {"text": "r165:aa957ed78c35 (default)", "id": "aa957ed78c35a1541f508d2ec90e501b0a9e3167"}, {"text": "r140:48e11b73e94c (default)", "id": "48e11b73e94c0db33e736eaeea692f990cb0b5f1"}, {"text": "r126:adf3cbf48329 (default)", "id": "adf3cbf483298563b968a6c673cd5bde5f7d5eea"}, {"text": "r113:6249fd0fb2cf (git)", "id": "6249fd0fb2cfb1411e764129f598e2cf0de79a6f"}, {"text": "r109:75feb4c33e81 (default)", "id": "75feb4c33e81186c87eac740cee2447330288412"}, {"text": "r108:9a4dc232ecdc (default)", "id": "9a4dc232ecdc763ef2e98ae2238cfcbba4f6ad8d"}, {"text": "r107:595cce4efa21 (default)", "id": "595cce4efa21fda2f2e4eeb4fe5f2a6befe6fa2d"}, {"text": "r104:4a8bd421fbc2 (default)", "id": "4a8bd421fbc2dfbfb70d85a3fe064075ab2c49da"}, {"text": "r102:57be63fc8f85 (default)", "id": "57be63fc8f85e65a0106a53187f7316f8c487ffa"}, {"text": "r101:5530bd87f7e2 (git)", "id": "5530bd87f7e2e124a64d07cb2654c997682128be"}, {"text": "r99:e516008b1c93 (default)", "id": "e516008b1c93f142263dc4b7961787cbad654ce1"}, {"text": "r93:41f43fc74b8b (default)", "id": "41f43fc74b8b285984554532eb105ac3be5c434f"}, {"text": "r92:cc66b61b8455 (default)", "id": "cc66b61b8455b264a7a8a2d8ddc80fcfc58c221e"}, {"text": "r91:73ab5b616b32 (default)", "id": "73ab5b616b3271b0518682fb4988ce421de8099f"}, {"text": "r82:e0da75f308c0 (default)", "id": "e0da75f308c0f18f98e9ce6257626009fdda2b39"}, {"text": "r81:fb2e41e0f081 (default)", "id": "fb2e41e0f0810be4d7103bc2a4c7be16ee3ec611"}, {"text": "r76:602ae2f5e7ad (default)", "id": "602ae2f5e7ade70b3b66a58cdd9e3e613dc8a028"}, {"text": "r73:a066b25d5df7 (default)", "id": "a066b25d5df7016b45a41b7e2a78c33b57adc235"}, {"text": "r61:637a933c9059 (web)", "id": "637a933c905958ce5151f154147c25c1c7b68832"}, {"text": "r60:0c21004effeb (web)", "id": "0c21004effeb8ce2d2d5b4a8baf6afa8394b6fbc"}, {"text": "r59:a1f39c56d3f1 (web)", "id": "a1f39c56d3f1d52d5fb5920370a2a2716cd9a444"}, {"text": "r58:97d32df05c71 (web)", "id": "97d32df05c715a3bbf936bf3cc4e32fb77fe1a7f"}, {"text": "r57:08eaf1451771 (web)", "id": "08eaf14517718dccea4b67755a93368341aca919"}, {"text": "r56:22f71ad26526 (web)", "id": "22f71ad265265a53238359c883aa976e725aa07d"}, {"text": "r49:97501f02b7b4 (web)", "id": "97501f02b7b4330924b647755663a2d90a5e638d"}, {"text": "r47:86ede6754f2b (web)", "id": "86ede6754f2b27309452bb11f997386ae01d0e5a"}, {"text": "r45:014c40c0203c (web)", "id": "014c40c0203c423dc19ecf94644f7cac9d4cdce0"}, {"text": "r30:ee87846a61c1 (default)", "id": "ee87846a61c12153b51543bf860e1026c6d3dcba"}, {"text": "r26:9bb326a04ae5 (default)", "id": "9bb326a04ae5d98d437dece54be04f830cf1edd9"}, {"text": "r24:536c1a194283 (default)", "id": "536c1a19428381cfea92ac44985304f6a8049569"}, {"text": "r8:dc5d2c0661b6 (default)", "id": "dc5d2c0661b61928834a785d3e64a3f80d3aad9c"}, {"text": "r7:3803844fdbd3 (default)", "id": "3803844fdbd3b711175fc3da9bdacfcd6d29a6fb"}]}, {"text": "Branches", "children": [{"text": "default", "id": "2062ec7beeeaf9f44a1c25c41479565040b930b2"}, {"text": "stable", "id": "4f7e2131323e0749a740c0a56ab68ae9269c562a"}]}, {"text": "Tags", "children": [{"text": "v0.2.0", "id": "2c96c02def9a7c997f33047761a53943e6254396"}, {"text": "v0.1.9", "id": "8680b1d1cee3aa3c1ab3734b76ee164bbedbc5c9"}, {"text": "v0.1.8", "id": "ecb25ba9c96faf1e65a0bc3fd914918420a2f116"}, {"text": "v0.1.7", "id": "f67633a2894edaf28513706d558205fa93df9209"}, {"text": "v0.1.6", "id": "02b38c0eb6f982174750c0e309ff9faddc0c7e12"}, {"text": "v0.1.5", "id": "a6664e18181c6fc81b751a8d01474e7e1a3fe7fc"}, {"text": "v0.1.4", "id": "fd4bdb5e9b2a29b4393a4ac6caef48c17ee1a200"}, {"text": "v0.1.3", "id": "17544fbfcd33ffb439e2b728b5d526b1ef30bfcf"}, {"text": "v0.1.2", "id": "a7e60bff65d57ac3a1a1ce3b12a70f8a9e8a7720"}, {"text": "v0.1.11", "id": "fef5bfe1dc17611d5fb59a7f6f95c55c3606f933"}, {"text": "v0.1.10", "id": "92831aebf2f8dd4879e897024b89d09af214df1c"}, {"text": "v0.1.1", "id": "eb3a60fc964309c1a318b8dfe26aa2d1586c85ae"}, {"text": "tip", "id": "2062ec7beeeaf9f44a1c25c41479565040b930b2"}]}], "more": false}
1 {"results": [{"text": "Changesets", "children": [{"text": "r648:dbec37a0d5ca (default)", "type": "sha", "id": "dbec37a0d5cab8ff39af4cfc4a4cd3996e4acfc6"}, {"text": "r639:1d20ed9eda94 (default)", "type": "sha", "id": "1d20ed9eda9482d46ff0a6af5812550218b3ff15"}, {"text": "r547:0173395e8227 (default)", "type": "sha", "id": "0173395e822797f098799ed95c1a81b6a547a9ad"}, {"text": "r546:afbb45ade933 (default)", "type": "sha", "id": "afbb45ade933a8182f1d8ec5d4d1bb2de2572043"}, {"text": "r502:6f093e30cac3 (default)", "type": "sha", "id": "6f093e30cac34e6b4b11275a9f22f80c5d7ad1f7"}, {"text": "r476:c7e2212dd2ae (default)", "type": "sha", "id": "c7e2212dd2ae975d1d06534a3d7e317165c06960"}, {"text": "r472:45477506df79 (default)", "type": "sha", "id": "45477506df79f701bf69419aac3e1f0fed3c5bcf"}, {"text": "r469:5fc76cb25d11 (default)", "type": "sha", "id": "5fc76cb25d11e07c60de040f78b8cd265ff10d53"}, {"text": "r468:b073433cf899 (default)", "type": "sha", "id": "b073433cf8994969ee5cd7cce84cbe587bb880b2"}, {"text": "r467:7a74dbfcacd1 (default)", "type": "sha", "id": "7a74dbfcacd1dbcb58bb9c860b2f29fbb22c4c96"}, {"text": "r465:71ee52cc4d62 (default)", "type": "sha", "id": "71ee52cc4d629096bdbee036325975dac2af4501"}, {"text": "r452:a5b217d26c5f (default)", "type": "sha", "id": "a5b217d26c5f111e72bae4de672b084ee0fbf75c"}, {"text": "r450:47aedd538bf6 (default)", "type": "sha", "id": "47aedd538bf616eedcb0e7d630ea476df0e159c7"}, {"text": "r432:8e4915fa32d7 (default)", "type": "sha", "id": "8e4915fa32d727dcbf09746f637a5f82e539511e"}, {"text": "r356:25213a5fbb04 (default)", "type": "sha", "id": "25213a5fbb048dff8ba65d21e466a835536e5b70"}, {"text": "r351:23debcedddc1 (default)", "type": "sha", "id": "23debcedddc1c23c14be33e713e7786d4a9de471"}, {"text": "r342:61e25b2a90a1 (default)", "type": "sha", "id": "61e25b2a90a19e7fffd75dea1e4c7e20df526bbe"}, {"text": "r318:fb95b340e0d0 (webvcs)", "type": "sha", "id": "fb95b340e0d03fa51f33c56c991c08077c99303e"}, {"text": "r303:bda35e0e564f (default)", "type": "sha", "id": "bda35e0e564fbbc5cd26fe0a37fb647a254c99fe"}, {"text": "r302:97ff74896d7d (default)", "type": "sha", "id": "97ff74896d7dbf3115a337a421d44b55154acc89"}, {"text": "r293:cec3473c3fdb (default)", "type": "sha", "id": "cec3473c3fdb9599c98067182a075b49bde570f9"}, {"text": "r289:0e86c43eef86 (default)", "type": "sha", "id": "0e86c43eef866a013a587666a877c879899599bb"}, {"text": "r288:91a27c312808 (default)", "type": "sha", "id": "91a27c312808100cf20a602f78befbbff9d89bfd"}, {"text": "r287:400e36a1670a (default)", "type": "sha", "id": "400e36a1670a57d11e3edcb5b07bf82c30006d0b"}, {"text": "r261:014fb17dfc95 (default)", "type": "sha", "id": "014fb17dfc95b0995e838c565376bf9a993e230a"}, {"text": "r260:cca7aebbc4d6 (default)", "type": "sha", "id": "cca7aebbc4d6125798446b11e69dc8847834a982"}, {"text": "r258:14cdb2957c01 (workdir)", "type": "sha", "id": "14cdb2957c011a5feba36f50d960d9832ba0f0c1"}, {"text": "r245:34df20118ed7 (default)", "type": "sha", "id": "34df20118ed74b5987d22a579e8a60e903da5bf8"}, {"text": "r233:0375d9042a64 (workdir)", "type": "sha", "id": "0375d9042a64a1ac1641528f0f0668f9a339e86d"}, {"text": "r222:94aa45fc1806 (workdir)", "type": "sha", "id": "94aa45fc1806c04d4ba640933edf682c22478453"}, {"text": "r188:7ed99bc73881 (default)", "type": "sha", "id": "7ed99bc738818879941e3ce20243f8856a7cfc84"}, {"text": "r184:1e85975528bc (default)", "type": "sha", "id": "1e85975528bcebe853732a9e5fb8dbf4461f6bb2"}, {"text": "r183:ed30beddde7b (default)", "type": "sha", "id": "ed30beddde7bbddb26042625be19bcd11576c1dd"}, {"text": "r177:a6664e18181c (default)", "type": "sha", "id": "a6664e18181c6fc81b751a8d01474e7e1a3fe7fc"}, {"text": "r167:8911406ad776 (default)", "type": "sha", "id": "8911406ad776fdd3d0b9932a2e89677e57405a48"}, {"text": "r165:aa957ed78c35 (default)", "type": "sha", "id": "aa957ed78c35a1541f508d2ec90e501b0a9e3167"}, {"text": "r140:48e11b73e94c (default)", "type": "sha", "id": "48e11b73e94c0db33e736eaeea692f990cb0b5f1"}, {"text": "r126:adf3cbf48329 (default)", "type": "sha", "id": "adf3cbf483298563b968a6c673cd5bde5f7d5eea"}, {"text": "r113:6249fd0fb2cf (git)", "type": "sha", "id": "6249fd0fb2cfb1411e764129f598e2cf0de79a6f"}, {"text": "r109:75feb4c33e81 (default)", "type": "sha", "id": "75feb4c33e81186c87eac740cee2447330288412"}, {"text": "r108:9a4dc232ecdc (default)", "type": "sha", "id": "9a4dc232ecdc763ef2e98ae2238cfcbba4f6ad8d"}, {"text": "r107:595cce4efa21 (default)", "type": "sha", "id": "595cce4efa21fda2f2e4eeb4fe5f2a6befe6fa2d"}, {"text": "r104:4a8bd421fbc2 (default)", "type": "sha", "id": "4a8bd421fbc2dfbfb70d85a3fe064075ab2c49da"}, {"text": "r102:57be63fc8f85 (default)", "type": "sha", "id": "57be63fc8f85e65a0106a53187f7316f8c487ffa"}, {"text": "r101:5530bd87f7e2 (git)", "type": "sha", "id": "5530bd87f7e2e124a64d07cb2654c997682128be"}, {"text": "r99:e516008b1c93 (default)", "type": "sha", "id": "e516008b1c93f142263dc4b7961787cbad654ce1"}, {"text": "r93:41f43fc74b8b (default)", "type": "sha", "id": "41f43fc74b8b285984554532eb105ac3be5c434f"}, {"text": "r92:cc66b61b8455 (default)", "type": "sha", "id": "cc66b61b8455b264a7a8a2d8ddc80fcfc58c221e"}, {"text": "r91:73ab5b616b32 (default)", "type": "sha", "id": "73ab5b616b3271b0518682fb4988ce421de8099f"}, {"text": "r82:e0da75f308c0 (default)", "type": "sha", "id": "e0da75f308c0f18f98e9ce6257626009fdda2b39"}, {"text": "r81:fb2e41e0f081 (default)", "type": "sha", "id": "fb2e41e0f0810be4d7103bc2a4c7be16ee3ec611"}, {"text": "r76:602ae2f5e7ad (default)", "type": "sha", "id": "602ae2f5e7ade70b3b66a58cdd9e3e613dc8a028"}, {"text": "r73:a066b25d5df7 (default)", "type": "sha", "id": "a066b25d5df7016b45a41b7e2a78c33b57adc235"}, {"text": "r61:637a933c9059 (web)", "type": "sha", "id": "637a933c905958ce5151f154147c25c1c7b68832"}, {"text": "r60:0c21004effeb (web)", "type": "sha", "id": "0c21004effeb8ce2d2d5b4a8baf6afa8394b6fbc"}, {"text": "r59:a1f39c56d3f1 (web)", "type": "sha", "id": "a1f39c56d3f1d52d5fb5920370a2a2716cd9a444"}, {"text": "r58:97d32df05c71 (web)", "type": "sha", "id": "97d32df05c715a3bbf936bf3cc4e32fb77fe1a7f"}, {"text": "r57:08eaf1451771 (web)", "type": "sha", "id": "08eaf14517718dccea4b67755a93368341aca919"}, {"text": "r56:22f71ad26526 (web)", "type": "sha", "id": "22f71ad265265a53238359c883aa976e725aa07d"}, {"text": "r49:97501f02b7b4 (web)", "type": "sha", "id": "97501f02b7b4330924b647755663a2d90a5e638d"}, {"text": "r47:86ede6754f2b (web)", "type": "sha", "id": "86ede6754f2b27309452bb11f997386ae01d0e5a"}, {"text": "r45:014c40c0203c (web)", "type": "sha", "id": "014c40c0203c423dc19ecf94644f7cac9d4cdce0"}, {"text": "r30:ee87846a61c1 (default)", "type": "sha", "id": "ee87846a61c12153b51543bf860e1026c6d3dcba"}, {"text": "r26:9bb326a04ae5 (default)", "type": "sha", "id": "9bb326a04ae5d98d437dece54be04f830cf1edd9"}, {"text": "r24:536c1a194283 (default)", "type": "sha", "id": "536c1a19428381cfea92ac44985304f6a8049569"}, {"text": "r8:dc5d2c0661b6 (default)", "type": "sha", "id": "dc5d2c0661b61928834a785d3e64a3f80d3aad9c"}, {"text": "r7:3803844fdbd3 (default)", "type": "sha", "id": "3803844fdbd3b711175fc3da9bdacfcd6d29a6fb"}]}, {"text": "Branches", "children": [{"text": "default", "type": "branch", "id": "2062ec7beeeaf9f44a1c25c41479565040b930b2"}, {"text": "stable", "type": "branch", "id": "4f7e2131323e0749a740c0a56ab68ae9269c562a"}]}, {"text": "Tags", "children": [{"text": "v0.2.0", "type": "tag", "id": "2c96c02def9a7c997f33047761a53943e6254396"}, {"text": "v0.1.9", "type": "tag", "id": "8680b1d1cee3aa3c1ab3734b76ee164bbedbc5c9"}, {"text": "v0.1.8", "type": "tag", "id": "ecb25ba9c96faf1e65a0bc3fd914918420a2f116"}, {"text": "v0.1.7", "type": "tag", "id": "f67633a2894edaf28513706d558205fa93df9209"}, {"text": "v0.1.6", "type": "tag", "id": "02b38c0eb6f982174750c0e309ff9faddc0c7e12"}, {"text": "v0.1.5", "type": "tag", "id": "a6664e18181c6fc81b751a8d01474e7e1a3fe7fc"}, {"text": "v0.1.4", "type": "tag", "id": "fd4bdb5e9b2a29b4393a4ac6caef48c17ee1a200"}, {"text": "v0.1.3", "type": "tag", "id": "17544fbfcd33ffb439e2b728b5d526b1ef30bfcf"}, {"text": "v0.1.2", "type": "tag", "id": "a7e60bff65d57ac3a1a1ce3b12a70f8a9e8a7720"}, {"text": "v0.1.11", "type": "tag", "id": "fef5bfe1dc17611d5fb59a7f6f95c55c3606f933"}, {"text": "v0.1.10", "type": "tag", "id": "92831aebf2f8dd4879e897024b89d09af214df1c"}, {"text": "v0.1.1", "type": "tag", "id": "eb3a60fc964309c1a318b8dfe26aa2d1586c85ae"}, {"text": "tip", "type": "tag", "id": "2062ec7beeeaf9f44a1c25c41479565040b930b2"}]}], "more": false} No newline at end of file
@@ -1,1 +1,1 b''
1 {"more": false, "results": [{"text": "Changesets", "children": [{"text": "r15:16", "id": "16"}, {"text": "r12:13", "id": "13"}, {"text": "r7:8", "id": "8"}, {"text": "r3:4", "id": "4"}, {"text": "r2:3", "id": "3"}]}, {"text": "Branches", "children": [{"text": "branches/add-docs", "id": "branches/add-docs/example.py@26"}, {"text": "branches/argparse", "id": "branches/argparse/example.py@26"}, {"text": "trunk", "id": "trunk/example.py@26"}]}, {"text": "Tags", "children": [{"text": "tags/v0.1", "id": "tags/v0.1/example.py@26"}, {"text": "tags/v0.2", "id": "tags/v0.2/example.py@26"}, {"text": "tags/v0.3", "id": "tags/v0.3/example.py@26"}, {"text": "tags/v0.5", "id": "tags/v0.5/example.py@26"}]}]} No newline at end of file
1 {"results": [{"text": "Changesets", "children": [{"text": "r15:16", "type": "sha", "id": "16"}, {"text": "r12:13", "type": "sha", "id": "13"}, {"text": "r7:8", "type": "sha", "id": "8"}, {"text": "r3:4", "type": "sha", "id": "4"}, {"text": "r2:3", "type": "sha", "id": "3"}]}, {"text": "Branches", "children": [{"text": "branches/add-docs", "type": "branch", "id": "branches/add-docs/example.py@26"}, {"text": "branches/argparse", "type": "branch", "id": "branches/argparse/example.py@26"}, {"text": "trunk", "type": "branch", "id": "trunk/example.py@26"}]}, {"text": "Tags", "children": [{"text": "tags/v0.1", "type": "tag", "id": "tags/v0.1/example.py@26"}, {"text": "tags/v0.2", "type": "tag", "id": "tags/v0.2/example.py@26"}, {"text": "tags/v0.3", "type": "tag", "id": "tags/v0.3/example.py@26"}, {"text": "tags/v0.5", "type": "tag", "id": "tags/v0.5/example.py@26"}]}], "more": false} No newline at end of file
@@ -1,1 +1,1 b''
1 {"results": [{"text": "Changesets", "children": [{"text": "r382:383", "id": "383"}, {"text": "r323:324", "id": "324"}, {"text": "r322:323", "id": "323"}, {"text": "r299:300", "id": "300"}, {"text": "r277:278", "id": "278"}, {"text": "r273:274", "id": "274"}, {"text": "r270:271", "id": "271"}, {"text": "r269:270", "id": "270"}, {"text": "r263:264", "id": "264"}, {"text": "r261:262", "id": "262"}, {"text": "r251:252", "id": "252"}, {"text": "r208:209", "id": "209"}, {"text": "r202:203", "id": "203"}, {"text": "r173:174", "id": "174"}, {"text": "r172:173", "id": "173"}, {"text": "r171:172", "id": "172"}, {"text": "r145:146", "id": "146"}, {"text": "r144:145", "id": "145"}, {"text": "r140:141", "id": "141"}, {"text": "r134:135", "id": "135"}, {"text": "r107:108", "id": "108"}, {"text": "r106:107", "id": "107"}, {"text": "r100:101", "id": "101"}, {"text": "r94:95", "id": "95"}, {"text": "r85:86", "id": "86"}, {"text": "r73:74", "id": "74"}, {"text": "r72:73", "id": "73"}, {"text": "r71:72", "id": "72"}, {"text": "r69:70", "id": "70"}, {"text": "r67:68", "id": "68"}, {"text": "r63:64", "id": "64"}, {"text": "r62:63", "id": "63"}, {"text": "r61:62", "id": "62"}, {"text": "r50:51", "id": "51"}, {"text": "r49:50", "id": "50"}, {"text": "r48:49", "id": "49"}, {"text": "r47:48", "id": "48"}, {"text": "r46:47", "id": "47"}, {"text": "r45:46", "id": "46"}, {"text": "r41:42", "id": "42"}, {"text": "r39:40", "id": "40"}, {"text": "r37:38", "id": "38"}, {"text": "r25:26", "id": "26"}, {"text": "r23:24", "id": "24"}, {"text": "r8:9", "id": "9"}, {"text": "r7:8", "id": "8"}]}, {"text": "Branches", "children": []}, {"text": "Tags", "children": []}], "more": false} No newline at end of file
1 {"results": [{"text": "Changesets", "children": [{"text": "r382:383", "type": "sha", "id": "383"}, {"text": "r323:324", "type": "sha", "id": "324"}, {"text": "r322:323", "type": "sha", "id": "323"}, {"text": "r299:300", "type": "sha", "id": "300"}, {"text": "r277:278", "type": "sha", "id": "278"}, {"text": "r273:274", "type": "sha", "id": "274"}, {"text": "r270:271", "type": "sha", "id": "271"}, {"text": "r269:270", "type": "sha", "id": "270"}, {"text": "r263:264", "type": "sha", "id": "264"}, {"text": "r261:262", "type": "sha", "id": "262"}, {"text": "r251:252", "type": "sha", "id": "252"}, {"text": "r208:209", "type": "sha", "id": "209"}, {"text": "r202:203", "type": "sha", "id": "203"}, {"text": "r173:174", "type": "sha", "id": "174"}, {"text": "r172:173", "type": "sha", "id": "173"}, {"text": "r171:172", "type": "sha", "id": "172"}, {"text": "r145:146", "type": "sha", "id": "146"}, {"text": "r144:145", "type": "sha", "id": "145"}, {"text": "r140:141", "type": "sha", "id": "141"}, {"text": "r134:135", "type": "sha", "id": "135"}, {"text": "r107:108", "type": "sha", "id": "108"}, {"text": "r106:107", "type": "sha", "id": "107"}, {"text": "r100:101", "type": "sha", "id": "101"}, {"text": "r94:95", "type": "sha", "id": "95"}, {"text": "r85:86", "type": "sha", "id": "86"}, {"text": "r73:74", "type": "sha", "id": "74"}, {"text": "r72:73", "type": "sha", "id": "73"}, {"text": "r71:72", "type": "sha", "id": "72"}, {"text": "r69:70", "type": "sha", "id": "70"}, {"text": "r67:68", "type": "sha", "id": "68"}, {"text": "r63:64", "type": "sha", "id": "64"}, {"text": "r62:63", "type": "sha", "id": "63"}, {"text": "r61:62", "type": "sha", "id": "62"}, {"text": "r50:51", "type": "sha", "id": "51"}, {"text": "r49:50", "type": "sha", "id": "50"}, {"text": "r48:49", "type": "sha", "id": "49"}, {"text": "r47:48", "type": "sha", "id": "48"}, {"text": "r46:47", "type": "sha", "id": "47"}, {"text": "r45:46", "type": "sha", "id": "46"}, {"text": "r41:42", "type": "sha", "id": "42"}, {"text": "r39:40", "type": "sha", "id": "40"}, {"text": "r37:38", "type": "sha", "id": "38"}, {"text": "r25:26", "type": "sha", "id": "26"}, {"text": "r23:24", "type": "sha", "id": "24"}, {"text": "r8:9", "type": "sha", "id": "9"}, {"text": "r7:8", "type": "sha", "id": "8"}]}, {"text": "Branches", "children": []}, {"text": "Tags", "children": []}], "more": false} No newline at end of file
@@ -30,10 +30,13 b' def route_path(name, params=None, **kwar'
30 30
31 31 base_url = {
32 32 'home': '/',
33 'admin_home': ADMIN_PREFIX,
33 34 'repos':
34 35 ADMIN_PREFIX + '/repos',
35 36 'repo_groups':
36 37 ADMIN_PREFIX + '/repo_groups',
38 'repo_groups_data':
39 ADMIN_PREFIX + '/repo_groups_data',
37 40 'user_groups':
38 41 ADMIN_PREFIX + '/user_groups',
39 42 'user_groups_data':
@@ -50,32 +53,27 b' fixture = Fixture()'
50 53
51 54 class TestAdminDelegatedUser(TestController):
52 55
53 def test_regular_user_cannot_see_admin_interfaces(
54 self, user_util, xhr_header):
56 def test_regular_user_cannot_see_admin_interfaces(self, user_util, xhr_header):
55 57 user = user_util.create_user(password='qweqwe')
58 user_util.inherit_default_user_permissions(user.username, False)
59
56 60 self.log_user(user.username, 'qweqwe')
57 61
58 # check if in home view, such user doesn't see the "admin" menus
59 response = self.app.get(route_path('home'))
60
61 assert_response = response.assert_response()
62
63 assert_response.no_element_exists('li.local-admin-repos')
64 assert_response.no_element_exists('li.local-admin-repo-groups')
65 assert_response.no_element_exists('li.local-admin-user-groups')
62 # user doesn't have any access to resources so main admin page should 404
63 self.app.get(route_path('admin_home'), status=404)
66 64
67 65 response = self.app.get(route_path('repos'), status=200)
68 66 response.mustcontain('data: []')
69 67
70 response = self.app.get(route_path('repo_groups'), status=200)
71 response.mustcontain('data: []')
68 response = self.app.get(route_path('repo_groups_data'),
69 status=200, extra_environ=xhr_header)
70 assert response.json['data'] == []
72 71
73 72 response = self.app.get(route_path('user_groups_data'),
74 73 status=200, extra_environ=xhr_header)
75 74 assert response.json['data'] == []
76 75
77 def test_regular_user_can_see_admin_interfaces_if_owner(
78 self, user_util, xhr_header):
76 def test_regular_user_can_see_admin_interfaces_if_owner(self, user_util, xhr_header):
79 77 user = user_util.create_user(password='qweqwe')
80 78 username = user.username
81 79
@@ -89,20 +87,21 b' class TestAdminDelegatedUser(TestControl'
89 87 user_group_name = user_group.users_group_name
90 88
91 89 self.log_user(username, 'qweqwe')
92 # check if in home view, such user doesn't see the "admin" menus
93 response = self.app.get(route_path('home'))
90
91 response = self.app.get(route_path('admin_home'))
94 92
95 93 assert_response = response.assert_response()
96 94
97 assert_response.one_element_exists('li.local-admin-repos')
98 assert_response.one_element_exists('li.local-admin-repo-groups')
99 assert_response.one_element_exists('li.local-admin-user-groups')
95 assert_response.element_contains('td.delegated-admin-repos', '1')
96 assert_response.element_contains('td.delegated-admin-repo-groups', '1')
97 assert_response.element_contains('td.delegated-admin-user-groups', '1')
100 98
101 99 # admin interfaces have visible elements
102 100 response = self.app.get(route_path('repos'), status=200)
103 101 response.mustcontain('"name_raw": "{}"'.format(repo_name))
104 102
105 response = self.app.get(route_path('repo_groups'), status=200)
103 response = self.app.get(route_path('repo_groups_data'),
104 extra_environ=xhr_header, status=200)
106 105 response.mustcontain('"name_raw": "{}"'.format(repo_group_name))
107 106
108 107 response = self.app.get(route_path('user_groups_data'),
@@ -132,19 +131,20 b' class TestAdminDelegatedUser(TestControl'
132 131
133 132 self.log_user(username, 'qweqwe')
134 133 # check if in home view, such user doesn't see the "admin" menus
135 response = self.app.get(route_path('home'))
134 response = self.app.get(route_path('admin_home'))
136 135
137 136 assert_response = response.assert_response()
138 137
139 assert_response.one_element_exists('li.local-admin-repos')
140 assert_response.one_element_exists('li.local-admin-repo-groups')
141 assert_response.one_element_exists('li.local-admin-user-groups')
138 assert_response.element_contains('td.delegated-admin-repos', '1')
139 assert_response.element_contains('td.delegated-admin-repo-groups', '1')
140 assert_response.element_contains('td.delegated-admin-user-groups', '1')
142 141
143 142 # admin interfaces have visible elements
144 143 response = self.app.get(route_path('repos'), status=200)
145 144 response.mustcontain('"name_raw": "{}"'.format(repo_name))
146 145
147 response = self.app.get(route_path('repo_groups'), status=200)
146 response = self.app.get(route_path('repo_groups_data'),
147 extra_environ=xhr_header, status=200)
148 148 response.mustcontain('"name_raw": "{}"'.format(repo_group_name))
149 149
150 150 response = self.app.get(route_path('user_groups_data'),
@@ -121,7 +121,8 b' def test_get_config(user_util, baseapp, '
121 121 expected_config.update({
122 122 'git_update_server_info': False,
123 123 'git_lfs_enabled': False,
124 'git_lfs_store_path': git_config['git_lfs_store_path']
124 'git_lfs_store_path': git_config['git_lfs_store_path'],
125 'git_lfs_http_scheme': 'http'
125 126 })
126 127
127 128 assert git_config == expected_config
@@ -69,7 +69,7 b' class StubVCSController(simplevcs.Simple'
69 69 return self.stub_response_body
70 70 return fake_app
71 71
72 def _create_config(self, extras, repo_name):
72 def _create_config(self, extras, repo_name, scheme='http'):
73 73 return None
74 74
75 75
@@ -22,6 +22,7 b' import pytest'
22 22
23 23 from rhodecode.lib.encrypt import (
24 24 AESCipher, SignatureVerificationError, InvalidDecryptedValue)
25 from rhodecode.lib.encrypt2 import (Encryptor, InvalidToken)
25 26
26 27
27 28 class TestEncryptModule(object):
@@ -74,3 +75,59 b' class TestEncryptModule(object):'
74 75 assert isinstance(AESCipher(
75 76 'differentsecret', hmac=True, strict_verification=False
76 77 ).decrypt(enc), InvalidDecryptedValue)
78
79
80 class TestEncryptModule2(object):
81
82 @pytest.mark.parametrize(
83 "key, text",
84 [
85 ('a', 'short'),
86 ('a'*64, 'too long(trimmed to 32)'),
87 ('a'*32, 'just enough'),
88 ('ąćęćę', 'non asci'),
89 ('$asa$asa', 'special $ used'),
90 ]
91 )
92 def test_encryption(self, key, text):
93 enc = Encryptor(key).encrypt(text)
94 assert Encryptor(key).decrypt(enc) == text
95
96 def test_encryption_with_bad_key(self):
97 key = 'secretstring'
98 text = 'ihatemysql'
99 enc = Encryptor(key).encrypt(text)
100
101 assert Encryptor('differentsecret').decrypt(enc) == ''
102
103 def test_encryption_with_bad_key_raises(self):
104 key = 'secretstring'
105 text = 'ihatemysql'
106 enc = Encryptor(key).encrypt(text)
107
108 with pytest.raises(InvalidToken) as e:
109 Encryptor('differentsecret').decrypt(enc, safe=False)
110
111 assert 'InvalidToken' in str(e)
112
113 def test_encryption_with_bad_format_data(self):
114 key = 'secret'
115 text = 'ihatemysql'
116 enc = Encryptor(key).encrypt(text)
117 enc = '$xyz' + enc[3:]
118
119 with pytest.raises(ValueError) as e:
120 Encryptor(key).decrypt(enc, safe=False)
121
122 assert 'Encrypted Data has invalid format' in str(e)
123
124 def test_encryption_with_bad_data(self):
125 key = 'secret'
126 text = 'ihatemysql'
127 enc = Encryptor(key).encrypt(text)
128 enc = enc[:-5]
129
130 with pytest.raises(InvalidToken) as e:
131 Encryptor(key).decrypt(enc, safe=False)
132
133 assert 'InvalidToken' in str(e)
@@ -40,27 +40,52 b' def test_urlify_text(url, expected_url):'
40 40
41 41
42 42 @pytest.mark.parametrize('repo_name, commit_id, path, expected_result', [
43 # Simple case 1
44 ('repo', 'commit', 'a/b',
45 '<a href="/repo/files/commit/"><i class="icon-home"></i></a>'
46 ' / '
47 '<a href="/repo/files/commit/a">a</a>'
48 ' / '
49 'b'),
50
51 # Simple case
43 52 ('rX<X', 'cX<X', 'pX<X/aX<X/bX<X',
44 '<a class="pjax-link" href="/rX%3CX/files/cX%3CX/">rX&lt;X</a>/'
45 '<a class="pjax-link" href="/rX%3CX/files/cX%3CX/pX%3CX">pX&lt;X</a>/'
46 '<a class="pjax-link" href="/rX%3CX/files/cX%3CX/pX%3CX/aX%3CX">aX&lt;X'
47 '</a>/bX&lt;X'),
53 '<a href="/rX%3CX/files/cX%3CX/"><i class="icon-home"></i></a>'
54 ' / '
55 '<a href="/rX%3CX/files/cX%3CX/pX%3CX">pX&lt;X</a>'
56 ' / '
57 '<a href="/rX%3CX/files/cX%3CX/pX%3CX/aX%3CX">aX&lt;X</a>'
58 ' / '
59 'bX&lt;X'),
60
48 61 # Path with only one segment
49 62 ('rX<X', 'cX<X', 'pX<X',
50 '<a class="pjax-link" href="/rX%3CX/files/cX%3CX/">rX&lt;X</a>/pX&lt;X'),
63 '<a href="/rX%3CX/files/cX%3CX/"><i class="icon-home"></i></a>'
64 ' / '
65 'pX&lt;X'),
66
51 67 # Empty path
52 ('rX<X', 'cX<X', '', 'rX&lt;X'),
68 ('rX<X', 'cX<X', '',
69 '<i class="icon-home"></i>'),
70
71 # simple quote
53 72 ('rX"X', 'cX"X', 'pX"X/aX"X/bX"X',
54 '<a class="pjax-link" href="/rX%22X/files/cX%22X/">rX&#34;X</a>/'
55 '<a class="pjax-link" href="/rX%22X/files/cX%22X/pX%22X">pX&#34;X</a>/'
56 '<a class="pjax-link" href="/rX%22X/files/cX%22X/pX%22X/aX%22X">aX&#34;X'
57 '</a>/bX&#34;X'),
58 ], ids=['simple', 'one_segment', 'empty_path', 'simple_quote'])
73 '<a href="/rX%22X/files/cX%22X/"><i class="icon-home"></i></a>'
74 ' / '
75 '<a href="/rX%22X/files/cX%22X/pX%22X">pX&#34;X</a>'
76 ' / '
77 '<a href="/rX%22X/files/cX%22X/pX%22X/aX%22X">aX&#34;X</a>'
78 ' / '
79 'bX&#34;X'),
80
81 ], ids=['simple1', 'simple2', 'one_segment', 'empty_path', 'simple_quote'])
59 82 def test_files_breadcrumbs_xss(
60 83 repo_name, commit_id, path, app, expected_result):
61 84 result = helpers.files_breadcrumbs(repo_name, commit_id, path)
62 85 # Expect it to encode all path fragments properly. This is important
63 86 # because it returns an instance of `literal`.
87 if path != '':
88 expected_result = expected_result + helpers.files_icon.format(helpers.escape(path))
64 89 assert result == expected_result
65 90
66 91
@@ -501,8 +501,8 b' class TestCreateOrUpdateUi(object):'
501 501
502 502 def test_update(self, repo_stub, settings_util):
503 503 model = VcsSettingsModel(repo=repo_stub.repo_name)
504
505 largefiles, phases, evolve = model.HG_SETTINGS
504 # care about only 3 first settings
505 largefiles, phases, evolve = model.HG_SETTINGS[:3]
506 506
507 507 section = 'test-section'
508 508 key = 'test-key'
@@ -531,10 +531,11 b' class TestCreateOrUpdateRepoHgSettings(o'
531 531 with mock.patch.object(model, '_create_or_update_ui') as create_mock:
532 532 model.create_or_update_repo_hg_settings(self.FORM_DATA)
533 533 expected_calls = [
534 mock.call(model.repo_settings, 'extensions', 'largefiles',
535 active=False, value=''),
536 mock.call(model.repo_settings, 'extensions', 'evolve',
537 active=False, value=''),
534 mock.call(model.repo_settings, 'extensions', 'largefiles', active=False, value=''),
535 mock.call(model.repo_settings, 'extensions', 'evolve', active=False, value=''),
536 mock.call(model.repo_settings, 'experimental', 'evolution', active=False, value=''),
537 mock.call(model.repo_settings, 'experimental', 'evolution.exchange', active=False, value='no'),
538 mock.call(model.repo_settings, 'extensions', 'topic', active=False, value=''),
538 539 mock.call(model.repo_settings, 'phases', 'publish', value='False'),
539 540 ]
540 541 assert expected_calls == create_mock.call_args_list
@@ -589,17 +590,16 b' class TestCreateOrUpdateGlobalHgSettings'
589 590 with mock.patch.object(model, '_create_or_update_ui') as create_mock:
590 591 model.create_or_update_global_hg_settings(self.FORM_DATA)
591 592 expected_calls = [
592 mock.call(model.global_settings, 'extensions', 'largefiles',
593 active=False, value=''),
594 mock.call(model.global_settings, 'largefiles', 'usercache',
595 value='/example/largefiles-store'),
596 mock.call(model.global_settings, 'phases', 'publish',
597 value='False'),
598 mock.call(model.global_settings, 'extensions', 'hgsubversion',
599 active=False),
600 mock.call(model.global_settings, 'extensions', 'evolve',
601 active=False, value='')
593 mock.call(model.global_settings, 'extensions', 'largefiles', active=False, value=''),
594 mock.call(model.global_settings, 'largefiles', 'usercache', value='/example/largefiles-store'),
595 mock.call(model.global_settings, 'phases', 'publish', value='False'),
596 mock.call(model.global_settings, 'extensions', 'hgsubversion', active=False),
597 mock.call(model.global_settings, 'extensions', 'evolve', active=False, value=''),
598 mock.call(model.global_settings, 'experimental', 'evolution', active=False, value=''),
599 mock.call(model.global_settings, 'experimental', 'evolution.exchange', active=False, value='no'),
600 mock.call(model.global_settings, 'extensions', 'topic', active=False, value=''),
602 601 ]
602
603 603 assert expected_calls == create_mock.call_args_list
604 604
605 605 @pytest.mark.parametrize('field_to_remove', FORM_DATA.keys())
@@ -625,10 +625,8 b' class TestCreateOrUpdateGlobalGitSetting'
625 625 with mock.patch.object(model, '_create_or_update_ui') as create_mock:
626 626 model.create_or_update_global_git_settings(self.FORM_DATA)
627 627 expected_calls = [
628 mock.call(model.global_settings, 'vcs_git_lfs', 'enabled',
629 active=False, value=False),
630 mock.call(model.global_settings, 'vcs_git_lfs', 'store_location',
631 value='/example/lfs-store'),
628 mock.call(model.global_settings, 'vcs_git_lfs', 'enabled', active=False, value=False),
629 mock.call(model.global_settings, 'vcs_git_lfs', 'store_location', value='/example/lfs-store'),
632 630 ]
633 631 assert expected_calls == create_mock.call_args_list
634 632
@@ -512,7 +512,7 b' def test_outdated_comments('
512 512 (MergeFailureReason.HG_SOURCE_HAS_MORE_BRANCHES,
513 513 'This pull request cannot be merged because the source contains more branches than the target.'),
514 514 (MergeFailureReason.HG_TARGET_HAS_MULTIPLE_HEADS,
515 'This pull request cannot be merged because the target has multiple heads: `a,b,c`.'),
515 'This pull request cannot be merged because the target `ref_name` has multiple heads: `a,b,c`.'),
516 516 (MergeFailureReason.TARGET_IS_LOCKED,
517 517 'This pull request cannot be merged because the target repository is locked by user:123.'),
518 518 (MergeFailureReason.MISSING_TARGET_REF,
@@ -129,20 +129,19 b' def test_strip_with_single_heads(backend'
129 129 assert commit_ids['b'] not in rest_commit_ids
130 130
131 131
132 def test_get_nodes_returns_unicode_flat(backend_random):
133 repo = backend_random.repo
134 directories, files = scm.ScmModel().get_nodes(
135 repo.repo_name, repo.get_commit(commit_idx=0).raw_id,
136 flat=True)
132 def test_get_nodes_returns_unicode_flat(backend):
133 repo = backend.repo
134 commit_id = repo.get_commit(commit_idx=0).raw_id
135 directories, files = scm.ScmModel().get_nodes(repo.repo_name, commit_id, flat=True)
137 136 assert_contains_only_unicode(directories)
138 137 assert_contains_only_unicode(files)
139 138
140 139
141 def test_get_nodes_returns_unicode_non_flat(backend_random):
142 repo = backend_random.repo
143 directories, files = scm.ScmModel().get_nodes(
144 repo.repo_name, repo.get_commit(commit_idx=0).raw_id,
145 flat=False)
140 def test_get_nodes_returns_unicode_non_flat(backend):
141 repo = backend.repo
142 commit_id = repo.get_commit(commit_idx=0).raw_id
143
144 directories, files = scm.ScmModel().get_nodes(repo.repo_name, commit_id, flat=False)
146 145 # johbo: Checking only the names for now, since that is the critical
147 146 # part.
148 147 assert_contains_only_unicode([d['name'] for d in directories])
@@ -631,7 +631,9 b' class Backend(object):'
631 631 commits = commits or [
632 632 {'message': 'Commit %s of %s' % (x, self.repo_name)}
633 633 for x in range(number_of_commits)]
634 self._add_commits_to_repo(repo.scm_instance(), commits)
634 vcs_repo = repo.scm_instance()
635 vcs_repo.count()
636 self._add_commits_to_repo(vcs_repo, commits)
635 637 if heads:
636 638 self.pull_heads(repo, heads)
637 639
@@ -1224,7 +1226,7 b' class UserUtility(object):'
1224 1226 return user_group
1225 1227
1226 1228 def grant_user_permission(self, user_name, permission_name):
1227 self._inherit_default_user_permissions(user_name, False)
1229 self.inherit_default_user_permissions(user_name, False)
1228 1230 self.user_permissions.append((user_name, permission_name))
1229 1231
1230 1232 def grant_user_permission_to_repo_group(
@@ -1276,10 +1278,10 b' class UserUtility(object):'
1276 1278 return permission
1277 1279
1278 1280 def revoke_user_permission(self, user_name, permission_name):
1279 self._inherit_default_user_permissions(user_name, True)
1281 self.inherit_default_user_permissions(user_name, True)
1280 1282 UserModel().revoke_perm(user_name, permission_name)
1281 1283
1282 def _inherit_default_user_permissions(self, user_name, value):
1284 def inherit_default_user_permissions(self, user_name, value):
1283 1285 user = UserModel().get_by_username(user_name)
1284 1286 user.inherit_default_permissions = value
1285 1287 Session().add(user)
@@ -1884,3 +1886,17 b' def repo_groups(request):'
1884 1886 fixture.destroy_repo_group(parent_group)
1885 1887
1886 1888 return zombie_group, parent_group, child_group
1889
1890
1891 @pytest.fixture(scope="session")
1892 def tmp_path_factory(request):
1893 """Return a :class:`_pytest.tmpdir.TempPathFactory` instance for the test session.
1894 """
1895
1896 class TempPathFactory:
1897
1898 def mktemp(self, basename):
1899 import tempfile
1900 return tempfile.mktemp(basename)
1901
1902 return TempPathFactory()
@@ -48,9 +48,9 b' log = logging.getLogger(__name__)'
48 48
49 49
50 50 class CustomTestResponse(TestResponse):
51
51 52 def _save_output(self, out):
52 f = tempfile.NamedTemporaryFile(
53 delete=False, prefix='rc-test-', suffix='.html')
53 f = tempfile.NamedTemporaryFile(delete=False, prefix='rc-test-', suffix='.html')
54 54 f.write(out)
55 55 return f.name
56 56
@@ -63,6 +63,7 b' class CustomTestResponse(TestResponse):'
63 63
64 64 assert string in res
65 65 """
66 print_body = kw.pop('print_body', False)
66 67 if 'no' in kw:
67 68 no = kw['no']
68 69 del kw['no']
@@ -79,18 +80,20 b' class CustomTestResponse(TestResponse):'
79 80 for s in strings:
80 81 if not s in self:
81 82 print_stderr("Actual response (no %r):" % s)
82 print_stderr(str(self))
83 print_stderr("body output saved as `%s`" % f)
84 if print_body:
85 print_stderr(str(self))
83 86 raise IndexError(
84 "Body does not contain string %r, output saved as %s" % (
85 s, f))
87 "Body does not contain string %r, body output saved as %s" % (s, f))
86 88
87 89 for no_s in no:
88 90 if no_s in self:
89 91 print_stderr("Actual response (has %r)" % no_s)
90 print_stderr(str(self))
92 print_stderr("body output saved as `%s`" % f)
93 if print_body:
94 print_stderr(str(self))
91 95 raise IndexError(
92 "Body contains bad string %r, output saved as %s" % (
93 no_s, f))
96 "Body contains bad string %r, body output saved as %s" % (no_s, f))
94 97
95 98 def assert_response(self):
96 99 return AssertResponse(self)
@@ -99,8 +102,7 b' class CustomTestResponse(TestResponse):'
99 102 """
100 103 This returns the session from a response object.
101 104 """
102
103 from pyramid_beaker import session_factory_from_settings
105 from rhodecode.lib.rc_beaker import session_factory_from_settings
104 106 session = session_factory_from_settings(self.test_app._pyramid_settings)
105 107 return session(self.request)
106 108
@@ -390,6 +392,7 b' def is_url_reachable(url):'
390 392 try:
391 393 urllib2.urlopen(url)
392 394 except urllib2.URLError:
395 log.exception('URL Reach error')
393 396 return False
394 397 return True
395 398
@@ -148,7 +148,6 b' def _add_commits_to_repo(repo, commits):'
148 148 author=unicode(commit['author']),
149 149 date=commit['date'],
150 150 branch=commit.get('branch'))
151
152 151 return tip
153 152
154 153
@@ -97,7 +97,7 b' class TestArchives(BackendTestMixin):'
97 97 metafile = out.read('.archival.txt')
98 98
99 99 raw_id = self.tip.raw_id
100 assert 'rev:%s' % raw_id in metafile
100 assert 'commit_id:%s' % raw_id in metafile
101 101
102 102 for x in range(5):
103 103 node_path = '%d/file_%d.txt' % (x, x)
@@ -35,7 +35,7 b' from rhodecode.tests import get_new_dir'
35 35 from rhodecode.tests.vcs.conftest import BackendTestMixin
36 36
37 37
38 class TestBaseChangeset:
38 class TestBaseChangeset(object):
39 39
40 40 def test_is_deprecated(self):
41 41 from rhodecode.lib.vcs.backends.base import BaseChangeset
@@ -159,8 +159,7 b' class TestCommitsInNonEmptyRepo(BackendT'
159 159 parents=[initial],
160 160 branch=DEFAULT_BRANCH,)
161 161
162 default_branch_commits = self.repo.get_commits(
163 branch_name=DEFAULT_BRANCH)
162 default_branch_commits = self.repo.get_commits(branch_name=DEFAULT_BRANCH)
164 163 assert docs_branch_commit1 not in list(default_branch_commits)
165 164 assert docs_branch_commit2 not in list(default_branch_commits)
166 165
@@ -177,6 +176,10 b' class TestCommitsInNonEmptyRepo(BackendT'
177 176 commit_indexes = [c.idx for c in commits]
178 177 assert commit_indexes == [1, 2, 3, 7, 12, 15]
179 178
179 def test_get_commit_by_index(self):
180 for idx in [1, 2, 3, 4]:
181 assert idx == self.repo.get_commit(commit_idx=idx).idx
182
180 183 def test_get_commit_by_branch(self):
181 184 for branch, commit_id in self.repo.branches.iteritems():
182 185 assert commit_id == self.repo.get_commit(branch).raw_id
@@ -41,60 +41,41 b' from rhodecode.tests.vcs.conftest import'
41 41 pytestmark = pytest.mark.backends("git")
42 42
43 43
44 def repo_path_generator():
45 """
46 Return a different path to be used for cloning repos.
47 """
48 i = 0
49 while True:
50 i += 1
51 yield '%s-%d' % (TEST_GIT_REPO_CLONE, i)
52
53
54 REPO_PATH_GENERATOR = repo_path_generator()
55
56
57 class TestGitRepository:
58
59 # pylint: disable=protected-access
60
61 def __check_for_existing_repo(self):
62 if os.path.exists(TEST_GIT_REPO_CLONE):
63 self.fail('Cannot test git clone repo as location %s already '
64 'exists. You should manually remove it first.'
65 % TEST_GIT_REPO_CLONE)
44 class TestGitRepository(object):
66 45
67 46 @pytest.fixture(autouse=True)
68 47 def prepare(self, request, baseapp):
69 48 self.repo = GitRepository(TEST_GIT_REPO, bare=True)
70 49
71 def get_clone_repo(self):
50 def get_clone_repo(self, tmp_path_factory):
72 51 """
73 52 Return a non bare clone of the base repo.
74 53 """
75 clone_path = next(REPO_PATH_GENERATOR)
54 clone_path = tmp_path_factory.mktemp('clone-url')
76 55 repo_clone = GitRepository(
77 56 clone_path, create=True, src_url=self.repo.path, bare=False)
78 57
79 58 return repo_clone
80 59
81 def get_empty_repo(self, bare=False):
60 def get_empty_repo(self, tmp_path_factory, bare=False):
82 61 """
83 62 Return a non bare empty repo.
84 63 """
85 return GitRepository(next(REPO_PATH_GENERATOR), create=True, bare=bare)
64 clone_path = tmp_path_factory.mktemp('empty-repo')
65 return GitRepository(clone_path, create=True, bare=bare)
86 66
87 67 def test_wrong_repo_path(self):
88 68 wrong_repo_path = '/tmp/errorrepo_git'
89 69 with pytest.raises(RepositoryError):
90 70 GitRepository(wrong_repo_path)
91 71
92 def test_repo_clone(self):
93 self.__check_for_existing_repo()
72 def test_repo_clone(self, tmp_path_factory):
94 73 repo = GitRepository(TEST_GIT_REPO)
74 clone_path = tmp_path_factory.mktemp('_') + '_' + TEST_GIT_REPO_CLONE
95 75 repo_clone = GitRepository(
96 TEST_GIT_REPO_CLONE,
76 clone_path,
97 77 src_url=TEST_GIT_REPO, create=True, do_workspace_checkout=True)
78
98 79 assert len(repo.commit_ids) == len(repo_clone.commit_ids)
99 80 # Checking hashes of commits should be enough
100 81 for commit in repo.get_commits():
@@ -106,9 +87,10 b' class TestGitRepository:'
106 87 GitRepository(
107 88 TEST_GIT_REPO_CLONE + '_wo_create', src_url=TEST_GIT_REPO)
108 89
109 def test_repo_clone_with_update(self):
90 def test_repo_clone_with_update(self, tmp_path_factory):
110 91 repo = GitRepository(TEST_GIT_REPO)
111 clone_path = TEST_GIT_REPO_CLONE + '_with_update'
92 clone_path = tmp_path_factory.mktemp('_') + '_' + TEST_GIT_REPO_CLONE + '_update'
93
112 94 repo_clone = GitRepository(
113 95 clone_path,
114 96 create=True, src_url=TEST_GIT_REPO, do_workspace_checkout=True)
@@ -118,9 +100,9 b' class TestGitRepository:'
118 100 fpath = os.path.join(clone_path, 'MANIFEST.in')
119 101 assert os.path.isfile(fpath)
120 102
121 def test_repo_clone_without_update(self):
103 def test_repo_clone_without_update(self, tmp_path_factory):
122 104 repo = GitRepository(TEST_GIT_REPO)
123 clone_path = TEST_GIT_REPO_CLONE + '_without_update'
105 clone_path = tmp_path_factory.mktemp('_') + '_' + TEST_GIT_REPO_CLONE + '_without_update'
124 106 repo_clone = GitRepository(
125 107 clone_path,
126 108 create=True, src_url=TEST_GIT_REPO, do_workspace_checkout=False)
@@ -131,9 +113,9 b' class TestGitRepository:'
131 113 assert not repo_clone.bare
132 114 assert not os.path.isfile(fpath)
133 115
134 def test_repo_clone_into_bare_repo(self):
116 def test_repo_clone_into_bare_repo(self, tmp_path_factory):
135 117 repo = GitRepository(TEST_GIT_REPO)
136 clone_path = TEST_GIT_REPO_CLONE + '_bare.git'
118 clone_path = tmp_path_factory.mktemp('_') + '_' + TEST_GIT_REPO_CLONE + '_bare.git'
137 119 repo_clone = GitRepository(
138 120 clone_path, create=True, src_url=repo.path, bare=True)
139 121 assert repo_clone.bare
@@ -275,8 +257,8 b' TODO: To be written...'
275 257 def test_head(self):
276 258 assert self.repo.head == self.repo.get_commit().raw_id
277 259
278 def test_checkout_with_create(self):
279 repo_clone = self.get_clone_repo()
260 def test_checkout_with_create(self, tmp_path_factory):
261 repo_clone = self.get_clone_repo(tmp_path_factory)
280 262
281 263 new_branch = 'new_branch'
282 264 assert repo_clone._current_branch() == 'master'
@@ -288,22 +270,22 b' TODO: To be written...'
288 270 assert set(repo_clone.branches) == {'master', new_branch}
289 271 assert repo_clone._current_branch() == new_branch
290 272
291 def test_checkout(self):
292 repo_clone = self.get_clone_repo()
273 def test_checkout(self, tmp_path_factory):
274 repo_clone = self.get_clone_repo(tmp_path_factory)
293 275
294 276 repo_clone._checkout('new_branch', create=True)
295 277 repo_clone._checkout('master')
296 278
297 279 assert repo_clone._current_branch() == 'master'
298 280
299 def test_checkout_same_branch(self):
300 repo_clone = self.get_clone_repo()
281 def test_checkout_same_branch(self, tmp_path_factory):
282 repo_clone = self.get_clone_repo(tmp_path_factory)
301 283
302 284 repo_clone._checkout('master')
303 285 assert repo_clone._current_branch() == 'master'
304 286
305 def test_checkout_branch_already_exists(self):
306 repo_clone = self.get_clone_repo()
287 def test_checkout_branch_already_exists(self, tmp_path_factory):
288 repo_clone = self.get_clone_repo(tmp_path_factory)
307 289
308 290 with pytest.raises(RepositoryError):
309 291 repo_clone._checkout('master', create=True)
@@ -316,32 +298,32 b' TODO: To be written...'
316 298 with pytest.raises(RepositoryError):
317 299 self.repo._current_branch()
318 300
319 def test_current_branch_empty_repo(self):
320 repo = self.get_empty_repo()
301 def test_current_branch_empty_repo(self, tmp_path_factory):
302 repo = self.get_empty_repo(tmp_path_factory)
321 303 assert repo._current_branch() is None
322 304
323 def test_local_clone(self):
324 clone_path = next(REPO_PATH_GENERATOR)
305 def test_local_clone(self, tmp_path_factory):
306 clone_path = tmp_path_factory.mktemp('test-local-clone')
325 307 self.repo._local_clone(clone_path, 'master')
326 308 repo_clone = GitRepository(clone_path)
327 309
328 310 assert self.repo.commit_ids == repo_clone.commit_ids
329 311
330 def test_local_clone_with_specific_branch(self):
331 source_repo = self.get_clone_repo()
312 def test_local_clone_with_specific_branch(self, tmp_path_factory):
313 source_repo = self.get_clone_repo(tmp_path_factory)
332 314
333 315 # Create a new branch in source repo
334 316 new_branch_commit = source_repo.commit_ids[-3]
335 317 source_repo._checkout(new_branch_commit)
336 318 source_repo._checkout('new_branch', create=True)
337 319
338 clone_path = next(REPO_PATH_GENERATOR)
320 clone_path = tmp_path_factory.mktemp('git-clone-path-1')
339 321 source_repo._local_clone(clone_path, 'new_branch')
340 322 repo_clone = GitRepository(clone_path)
341 323
342 324 assert source_repo.commit_ids[:-3 + 1] == repo_clone.commit_ids
343 325
344 clone_path = next(REPO_PATH_GENERATOR)
326 clone_path = tmp_path_factory.mktemp('git-clone-path-2')
345 327 source_repo._local_clone(clone_path, 'master')
346 328 repo_clone = GitRepository(clone_path)
347 329
@@ -351,9 +333,9 b' TODO: To be written...'
351 333 with pytest.raises(RepositoryError):
352 334 self.repo._local_clone(self.repo.path, 'master')
353 335
354 def test_local_fetch(self):
355 target_repo = self.get_empty_repo()
356 source_repo = self.get_clone_repo()
336 def test_local_fetch(self, tmp_path_factory):
337 target_repo = self.get_empty_repo(tmp_path_factory)
338 source_repo = self.get_clone_repo(tmp_path_factory)
357 339
358 340 # Create a new branch in source repo
359 341 master_commit = source_repo.commit_ids[-1]
@@ -367,8 +349,8 b' TODO: To be written...'
367 349 target_repo._local_fetch(source_repo.path, 'master')
368 350 assert target_repo._last_fetch_heads() == [master_commit]
369 351
370 def test_local_fetch_from_bare_repo(self):
371 target_repo = self.get_empty_repo()
352 def test_local_fetch_from_bare_repo(self, tmp_path_factory):
353 target_repo = self.get_empty_repo(tmp_path_factory)
372 354 target_repo._local_fetch(self.repo.path, 'master')
373 355
374 356 master_commit = self.repo.commit_ids[-1]
@@ -378,15 +360,15 b' TODO: To be written...'
378 360 with pytest.raises(ValueError):
379 361 self.repo._local_fetch(self.repo.path, 'master')
380 362
381 def test_local_fetch_branch_does_not_exist(self):
382 target_repo = self.get_empty_repo()
363 def test_local_fetch_branch_does_not_exist(self, tmp_path_factory):
364 target_repo = self.get_empty_repo(tmp_path_factory)
383 365
384 366 with pytest.raises(RepositoryError):
385 367 target_repo._local_fetch(self.repo.path, 'new_branch')
386 368
387 def test_local_pull(self):
388 target_repo = self.get_empty_repo()
389 source_repo = self.get_clone_repo()
369 def test_local_pull(self, tmp_path_factory):
370 target_repo = self.get_empty_repo(tmp_path_factory)
371 source_repo = self.get_clone_repo(tmp_path_factory)
390 372
391 373 # Create a new branch in source repo
392 374 master_commit = source_repo.commit_ids[-1]
@@ -406,9 +388,9 b' TODO: To be written...'
406 388 with pytest.raises(RepositoryError):
407 389 self.repo._local_pull(self.repo.path, 'master')
408 390
409 def test_local_merge(self):
410 target_repo = self.get_empty_repo()
411 source_repo = self.get_clone_repo()
391 def test_local_merge(self, tmp_path_factory):
392 target_repo = self.get_empty_repo(tmp_path_factory)
393 source_repo = self.get_clone_repo(tmp_path_factory)
412 394
413 395 # Create a new branch in source repo
414 396 master_commit = source_repo.commit_ids[-1]
@@ -449,8 +431,8 b' TODO: To be written...'
449 431 assert not os.path.exists(
450 432 os.path.join(target_repo.path, '.git', 'MERGE_HEAD'))
451 433
452 def test_local_merge_into_empty_repo(self):
453 target_repo = self.get_empty_repo()
434 def test_local_merge_into_empty_repo(self, tmp_path_factory):
435 target_repo = self.get_empty_repo(tmp_path_factory)
454 436
455 437 # This is required as one cannot do a -ff-only merge in an empty repo.
456 438 target_repo._local_fetch(self.repo.path, 'master')
@@ -464,8 +446,8 b' TODO: To be written...'
464 446 self.repo._local_merge(
465 447 'merge_message', 'user name', 'user@name.com', None)
466 448
467 def test_local_push_non_bare(self):
468 target_repo = self.get_empty_repo()
449 def test_local_push_non_bare(self, tmp_path_factory):
450 target_repo = self.get_empty_repo(tmp_path_factory)
469 451
470 452 pushed_branch = 'pushed_branch'
471 453 self.repo._local_push('master', target_repo.path, pushed_branch)
@@ -479,8 +461,8 b' TODO: To be written...'
479 461 assert (target_repo.branches[pushed_branch] ==
480 462 self.repo.branches['master'])
481 463
482 def test_local_push_bare(self):
483 target_repo = self.get_empty_repo(bare=True)
464 def test_local_push_bare(self, tmp_path_factory):
465 target_repo = self.get_empty_repo(tmp_path_factory, bare=True)
484 466
485 467 pushed_branch = 'pushed_branch'
486 468 self.repo._local_push('master', target_repo.path, pushed_branch)
@@ -494,8 +476,8 b' TODO: To be written...'
494 476 assert (target_repo.branches[pushed_branch] ==
495 477 self.repo.branches['master'])
496 478
497 def test_local_push_non_bare_target_branch_is_checked_out(self):
498 target_repo = self.get_clone_repo()
479 def test_local_push_non_bare_target_branch_is_checked_out(self, tmp_path_factory):
480 target_repo = self.get_clone_repo(tmp_path_factory)
499 481
500 482 pushed_branch = 'pushed_branch'
501 483 # Create a new branch in source repo
@@ -515,8 +497,8 b' TODO: To be written...'
515 497 with pytest.raises(RepositoryError):
516 498 self.repo._local_push('master', target_repo.path, 'master')
517 499
518 def test_hooks_can_be_enabled_via_env_variable_for_local_push(self):
519 target_repo = self.get_empty_repo(bare=True)
500 def test_hooks_can_be_enabled_via_env_variable_for_local_push(self, tmp_path_factory):
501 target_repo = self.get_empty_repo(tmp_path_factory, bare=True)
520 502
521 503 with mock.patch.object(self.repo, 'run_git_command') as run_mock:
522 504 self.repo._local_push(
@@ -540,8 +522,8 b' TODO: To be written...'
540 522 f.write('\n'.join(script_lines))
541 523 os.chmod(hook_path, 0o755)
542 524
543 def test_local_push_does_not_execute_hook(self):
544 target_repo = self.get_empty_repo()
525 def test_local_push_does_not_execute_hook(self, tmp_path_factory):
526 target_repo = self.get_empty_repo(tmp_path_factory)
545 527
546 528 pushed_branch = 'pushed_branch'
547 529 self._add_failing_hook(target_repo.path, 'pre-receive')
@@ -556,8 +538,8 b' TODO: To be written...'
556 538 assert (target_repo.branches[pushed_branch] ==
557 539 self.repo.branches['master'])
558 540
559 def test_local_push_executes_hook(self):
560 target_repo = self.get_empty_repo(bare=True)
541 def test_local_push_executes_hook(self, tmp_path_factory):
542 target_repo = self.get_empty_repo(tmp_path_factory, bare=True)
561 543 self._add_failing_hook(target_repo.path, 'pre-receive', bare=True)
562 544 with pytest.raises(RepositoryError):
563 545 self.repo._local_push(
@@ -1087,27 +1069,32 b' class TestGitSpecificWithRepo(BackendTes'
1087 1069 'base')
1088 1070
1089 1071 def test_get_diff_runs_git_command_with_hashes(self):
1072 comm1 = self.repo[0]
1073 comm2 = self.repo[1]
1090 1074 self.repo.run_git_command = mock.Mock(return_value=['', ''])
1091 self.repo.get_diff(self.repo[0], self.repo[1])
1075 self.repo.get_diff(comm1, comm2)
1076
1092 1077 self.repo.run_git_command.assert_called_once_with(
1093 1078 ['diff', '-U3', '--full-index', '--binary', '-p', '-M',
1094 '--abbrev=40', self.repo._get_commit_id(0),
1095 self.repo._get_commit_id(1)])
1079 '--abbrev=40', comm1.raw_id, comm2.raw_id])
1096 1080
1097 1081 def test_get_diff_runs_git_command_with_str_hashes(self):
1082 comm2 = self.repo[1]
1098 1083 self.repo.run_git_command = mock.Mock(return_value=['', ''])
1099 self.repo.get_diff(self.repo.EMPTY_COMMIT, self.repo[1])
1084 self.repo.get_diff(self.repo.EMPTY_COMMIT, comm2)
1100 1085 self.repo.run_git_command.assert_called_once_with(
1101 1086 ['show', '-U3', '--full-index', '--binary', '-p', '-M',
1102 '--abbrev=40', self.repo._get_commit_id(1)])
1087 '--abbrev=40', comm2.raw_id])
1103 1088
1104 1089 def test_get_diff_runs_git_command_with_path_if_its_given(self):
1090 comm1 = self.repo[0]
1091 comm2 = self.repo[1]
1105 1092 self.repo.run_git_command = mock.Mock(return_value=['', ''])
1106 self.repo.get_diff(self.repo[0], self.repo[1], 'foo')
1093 self.repo.get_diff(comm1, comm2, 'foo')
1107 1094 self.repo.run_git_command.assert_called_once_with(
1108 1095 ['diff', '-U3', '--full-index', '--binary', '-p', '-M',
1109 '--abbrev=40', self.repo._get_commit_id(0),
1110 self.repo._get_commit_id(1), '--', 'foo'])
1096 '--abbrev=40', self.repo._lookup_commit(0),
1097 comm2.raw_id, '--', 'foo'])
1111 1098
1112 1099
1113 1100 @pytest.mark.usefixtures("vcs_repository_support")
@@ -70,10 +70,13 b' class TestMercurialRemoteRepoInvalidatio'
70 70 tags[name] = raw_id
71 71
72 72 repo = backend_hg.repo.scm_instance()
73
73 74 with patch.object(repo, '_remote') as remote:
75 repo.tags = tags
74 76 remote.lookup.return_value = ('commit-id', 'commit-idx')
75 77 remote.tags.return_value = tags
76 78 remote._get_tags.return_value = tags
79 remote.is_empty.return_value = False
77 80 remote.tag.side_effect = add_tag
78 81
79 82 # Invoke method.
@@ -79,9 +79,17 b' class TestInMemoryCommit(BackendTestMixi'
79 79 self.commit()
80 80 self.assert_succesful_commit(nodes)
81 81
82 @pytest.mark.skip_backends(
83 'svn', reason="Svn does not support commits on branches.")
84 def test_add_on_branch(self, nodes):
82 @pytest.mark.backends("hg")
83 def test_add_on_branch_hg(self, nodes):
84 for node in nodes:
85 self.imc.add(node)
86 self.commit(branch=u'stable')
87 self.assert_succesful_commit(nodes)
88
89 @pytest.mark.backends("git")
90 def test_add_on_branch_git(self, nodes):
91 self.repo._checkout('stable', create=True)
92
85 93 for node in nodes:
86 94 self.imc.add(node)
87 95 self.commit(branch=u'stable')
@@ -54,6 +54,20 b' class TestVCSOperations(object):'
54 54 'hg clone', clone_url, tmpdir.strpath)
55 55 _check_proper_clone(stdout, stderr, 'hg')
56 56
57 def test_clone_hg_repo_by_admin_pull_protocol(self, rc_web_server, tmpdir):
58 clone_url = rc_web_server.repo_clone_url(HG_REPO)
59 stdout, stderr = Command('/tmp').execute(
60 'hg clone --pull', clone_url, tmpdir.strpath)
61 _check_proper_clone(stdout, stderr, 'hg')
62
63 def test_clone_hg_repo_by_admin_pull_stream_protocol(self, rc_web_server, tmpdir):
64 clone_url = rc_web_server.repo_clone_url(HG_REPO)
65 stdout, stderr = Command('/tmp').execute(
66 'hg clone --pull --stream', clone_url, tmpdir.strpath)
67 assert 'files to transfer,' in stdout
68 assert 'transferred 1.' in stdout
69 assert '114 files updated,' in stdout
70
57 71 def test_clone_git_repo_by_admin(self, rc_web_server, tmpdir):
58 72 clone_url = rc_web_server.repo_clone_url(GIT_REPO)
59 73 cmd = Command('/tmp')
@@ -46,6 +46,7 b' class TestVCSOperationsSpecial(object):'
46 46 cmd.execute('git clone', clone_url)
47 47
48 48 repo = GitRepository(os.path.join(tmpdir.strpath, empty_repo.repo_name))
49 repo._checkout('test', create=True)
49 50 repo.in_memory_commit.add(FileNode('file', content=''))
50 51 repo.in_memory_commit.commit(
51 52 message='Commit on branch test',
@@ -92,6 +92,7 b' def junk_form_data_detector(request):'
92 92
93 93 def sanity_check_factory(handler, registry):
94 94 def sanity_check(request):
95 log.debug('Checking current URL sanity for bad data')
95 96 try:
96 97 junk_encoding_detector(request)
97 98 bad_url_data_detector(request)
@@ -113,5 +114,5 b' def includeme(config):'
113 114 'pyramid.events.NewRequest')
114 115 config.add_subscriber('rhodecode.subscribers.add_request_user_context',
115 116 'pyramid.events.ContextFound')
117 config.add_tween('rhodecode.tweens.vcs_detection_tween_factory')
116 118 config.add_tween('rhodecode.tweens.sanity_check_factory')
117 config.add_tween('rhodecode.tweens.vcs_detection_tween_factory')
@@ -1,26 +0,0 b''
1 .. _permissions-info-add-group-ref:
2
3 Repository Administration
4 =========================
5
6 Repository permissions in |RCE| can be managed in a number of different ways.
7 This overview should give you an insight into how you could adopt particular
8 settings for your needs:
9
10 * Global |repo| permissions: This allows you to set the default permissions
11 for each new |repo| created within |RCE|, see :ref:`repo-default-ref`. All
12 |repos| created will inherit these permissions unless explicitly configured.
13 * Individual |repo| permissions: To set individual |repo| permissions,
14 see :ref:`set-repo-perms`.
15 * Repository Group permissions: This allows you to define the permissions for
16 a group, and all |repos| created within that group will inherit the same
17 permissions.
18
19 .. toctree::
20
21 repo-perm-steps
22 repo-extra-fields
23 repo-hooks
24 repo-issue-tracker
25 repo-vcs
26
1 NO CONTENT: file was removed, binary diff hidden
@@ -1,12 +0,0 b''
1 <%namespace name="base" file="/base/base.mako"/>
2
3 <div class="summary-detail-header">
4 <h4 class="item">
5 ${_('Commit Author')}
6 </h4>
7 </div>
8 <div class="sidebar-right-content">
9 ${base.gravatar_with_user(c.commit.author)}
10 <div class="user-inline-data">- ${h.age_component(c.commit.date)}</div>
11 </div>
12
General Comments 0
You need to be logged in to leave comments. Login now