Merge remote-tracking branch 'origin/master' into nomenclature
Conflicts: endpoints/common.py endpoints/notificationhelper.py test/data/test.db workers/dockerfilebuild.py
This commit is contained in:
commit
1461310ab8
200 changed files with 240935 additions and 798 deletions
|
@ -1,4 +1,4 @@
|
|||
FROM phusion/baseimage:0.9.13
|
||||
FROM phusion/baseimage:0.9.15
|
||||
|
||||
ENV DEBIAN_FRONTEND noninteractive
|
||||
ENV HOME /root
|
||||
|
@ -7,13 +7,15 @@ ENV HOME /root
|
|||
RUN apt-get update # 10SEP2014
|
||||
|
||||
# New ubuntu packages should be added as their own apt-get install lines below the existing install commands
|
||||
RUN apt-get install -y git python-virtualenv python-dev libjpeg8 libjpeg62-dev libevent-dev gdebi-core g++ libmagic1 phantomjs nodejs npm libldap2-dev libsasl2-dev libpq-dev
|
||||
RUN apt-get install -y git python-virtualenv python-dev libjpeg8 libjpeg62 libjpeg62-dev libevent-2.0.5 libevent-dev gdebi-core g++ libmagic1 phantomjs nodejs npm libldap-2.4-2 libldap2-dev libsasl2-modules libsasl2-dev libpq5 libpq-dev
|
||||
|
||||
# Build the python dependencies
|
||||
ADD requirements.txt requirements.txt
|
||||
RUN virtualenv --distribute venv
|
||||
RUN venv/bin/pip install -r requirements.txt
|
||||
|
||||
RUN apt-get remove -y --auto-remove python-dev g++ libjpeg62-dev libevent-dev libldap2-dev libsasl2-dev libpq-dev
|
||||
|
||||
### End common section ###
|
||||
|
||||
RUN apt-get install -y lxc aufs-tools
|
||||
|
@ -30,6 +32,10 @@ ADD conf/init/preplogsdir.sh /etc/my_init.d/
|
|||
ADD conf/init/tutumdocker /etc/service/tutumdocker
|
||||
ADD conf/init/dockerfilebuild /etc/service/dockerfilebuild
|
||||
|
||||
RUN apt-get remove -y --auto-remove nodejs npm git phantomjs
|
||||
RUN apt-get autoremove -y
|
||||
RUN apt-get clean && rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/*
|
||||
|
||||
VOLUME ["/var/lib/docker", "/var/lib/lxc", "/conf/stack", "/var/log"]
|
||||
|
||||
CMD ["/sbin/my_init"]
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
FROM phusion/baseimage:0.9.13
|
||||
FROM phusion/baseimage:0.9.15
|
||||
|
||||
ENV DEBIAN_FRONTEND noninteractive
|
||||
ENV HOME /root
|
||||
|
@ -7,13 +7,17 @@ ENV HOME /root
|
|||
RUN apt-get update # 10SEP2014
|
||||
|
||||
# New ubuntu packages should be added as their own apt-get install lines below the existing install commands
|
||||
RUN apt-get install -y git python-virtualenv python-dev libjpeg8 libjpeg62-dev libevent-dev gdebi-core g++ libmagic1 phantomjs nodejs npm libldap2-dev libsasl2-dev libpq-dev
|
||||
RUN apt-get install -y git python-virtualenv python-dev libjpeg8 libjpeg62 libjpeg62-dev libevent-2.0.5 libevent-dev gdebi-core g++ libmagic1 phantomjs nodejs npm libldap-2.4-2 libldap2-dev libsasl2-modules libsasl2-dev libpq5 libpq-dev
|
||||
|
||||
# Build the python dependencies
|
||||
ADD requirements.txt requirements.txt
|
||||
RUN virtualenv --distribute venv
|
||||
RUN venv/bin/pip install -r requirements.txt
|
||||
|
||||
RUN apt-get remove -y --auto-remove python-dev g++ libjpeg62-dev libevent-dev libldap2-dev libsasl2-dev libpq-dev
|
||||
|
||||
### End common section ###
|
||||
|
||||
# Install the binary dependencies
|
||||
ADD binary_dependencies binary_dependencies
|
||||
RUN gdebi --n binary_dependencies/*.deb
|
||||
|
@ -34,7 +38,9 @@ ADD conf/init/doupdatelimits.sh /etc/my_init.d/
|
|||
ADD conf/init/preplogsdir.sh /etc/my_init.d/
|
||||
ADD conf/init/runmigration.sh /etc/my_init.d/
|
||||
|
||||
ADD conf/init/gunicorn /etc/service/gunicorn
|
||||
ADD conf/init/gunicorn_web /etc/service/gunicorn_web
|
||||
ADD conf/init/gunicorn_registry /etc/service/gunicorn_registry
|
||||
ADD conf/init/gunicorn_verbs /etc/service/gunicorn_verbs
|
||||
ADD conf/init/nginx /etc/service/nginx
|
||||
ADD conf/init/diffsworker /etc/service/diffsworker
|
||||
ADD conf/init/notificationworker /etc/service/notificationworker
|
||||
|
@ -44,6 +50,9 @@ ADD conf/init/buildlogsarchiver /etc/service/buildlogsarchiver
|
|||
RUN mkdir static/fonts static/ldn
|
||||
RUN venv/bin/python -m external_libraries
|
||||
|
||||
RUN apt-get autoremove -y
|
||||
RUN apt-get clean && rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/*
|
||||
|
||||
# Run the tests
|
||||
RUN TEST=true venv/bin/python -m unittest discover
|
||||
|
||||
|
|
39
app.py
39
app.py
|
@ -3,7 +3,7 @@ import os
|
|||
import json
|
||||
import yaml
|
||||
|
||||
from flask import Flask as BaseFlask, Config as BaseConfig
|
||||
from flask import Flask as BaseFlask, Config as BaseConfig, request, Request
|
||||
from flask.ext.principal import Principal
|
||||
from flask.ext.login import LoginManager
|
||||
from flask.ext.mail import Mail
|
||||
|
@ -18,12 +18,12 @@ from data.users import UserAuthentication
|
|||
from util.analytics import Analytics
|
||||
from util.exceptionlog import Sentry
|
||||
from util.queuemetrics import QueueMetrics
|
||||
from util.names import urn_generator
|
||||
from data.billing import Billing
|
||||
from data.buildlogs import BuildLogs
|
||||
from data.archivedlogs import LogArchive
|
||||
from data.queue import WorkQueue
|
||||
from data.userevent import UserEventsBuilderModule
|
||||
from datetime import datetime
|
||||
|
||||
|
||||
class Config(BaseConfig):
|
||||
|
@ -60,6 +60,7 @@ LICENSE_FILENAME = 'conf/stack/license.enc'
|
|||
|
||||
app = Flask(__name__)
|
||||
logger = logging.getLogger(__name__)
|
||||
profile = logging.getLogger('profile')
|
||||
|
||||
|
||||
if 'TEST' in os.environ:
|
||||
|
@ -82,6 +83,37 @@ else:
|
|||
environ_config = json.loads(os.environ.get(OVERRIDE_CONFIG_KEY, '{}'))
|
||||
app.config.update(environ_config)
|
||||
|
||||
app.teardown_request(database.close_db_filter)
|
||||
|
||||
|
||||
class RequestWithId(Request):
|
||||
request_gen = staticmethod(urn_generator(['request']))
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
super(RequestWithId, self).__init__(*args, **kwargs)
|
||||
self.request_id = self.request_gen()
|
||||
|
||||
|
||||
@app.before_request
|
||||
def _request_start():
|
||||
profile.debug('Starting request: %s', request.path)
|
||||
|
||||
|
||||
@app.after_request
|
||||
def _request_end(r):
|
||||
profile.debug('Ending request: %s', request.path)
|
||||
return r
|
||||
|
||||
|
||||
class InjectingFilter(logging.Filter):
|
||||
def filter(self, record):
|
||||
record.msg = '[%s] %s' % (request.request_id, record.msg)
|
||||
return True
|
||||
|
||||
profile.addFilter(InjectingFilter())
|
||||
|
||||
app.request_class = RequestWithId
|
||||
|
||||
features.import_features(app.config)
|
||||
|
||||
Principal(app, use_sessions=False)
|
||||
|
@ -105,9 +137,6 @@ dockerfile_build_queue = WorkQueue(app.config['DOCKERFILE_BUILD_QUEUE_NAME'], tf
|
|||
reporter=queue_metrics.report)
|
||||
notification_queue = WorkQueue(app.config['NOTIFICATION_QUEUE_NAME'], tf)
|
||||
|
||||
# TODO: Remove this in the prod push following the notifications change.
|
||||
webhook_queue = WorkQueue(app.config['WEBHOOK_QUEUE_NAME'], tf)
|
||||
|
||||
database.configure(app.config)
|
||||
model.config.app_config = app.config
|
||||
model.config.store = storage
|
||||
|
|
|
@ -1,90 +1,14 @@
|
|||
import logging
|
||||
import logging.config
|
||||
import uuid
|
||||
|
||||
from peewee import Proxy
|
||||
|
||||
from app import app as application
|
||||
from flask import request, Request
|
||||
from util.names import urn_generator
|
||||
from data.database import db as model_db, read_slave
|
||||
|
||||
# Turn off debug logging for boto
|
||||
logging.getLogger('boto').setLevel(logging.CRITICAL)
|
||||
|
||||
from endpoints.api import api_bp
|
||||
from endpoints.index import index
|
||||
from endpoints.web import web
|
||||
from endpoints.tags import tags
|
||||
from endpoints.registry import registry
|
||||
from endpoints.verbs import verbs
|
||||
from endpoints.webhooks import webhooks
|
||||
from endpoints.realtime import realtime
|
||||
from endpoints.callbacks import callback
|
||||
|
||||
from logentries import LogentriesHandler
|
||||
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
# Bind all of the blueprints
|
||||
import web
|
||||
import verbs
|
||||
import registry
|
||||
|
||||
werkzeug = logging.getLogger('werkzeug')
|
||||
werkzeug.setLevel(logging.DEBUG)
|
||||
|
||||
profile = logging.getLogger('profile')
|
||||
profile.setLevel(logging.DEBUG)
|
||||
|
||||
logentries_key = application.config.get('LOGENTRIES_KEY', None)
|
||||
if logentries_key:
|
||||
logger.debug('Initializing logentries with key: %s' % logentries_key)
|
||||
werkzeug.addHandler(LogentriesHandler(logentries_key))
|
||||
profile.addHandler(LogentriesHandler(logentries_key))
|
||||
|
||||
application.register_blueprint(web)
|
||||
application.register_blueprint(callback, url_prefix='/oauth2')
|
||||
application.register_blueprint(index, url_prefix='/v1')
|
||||
application.register_blueprint(tags, url_prefix='/v1')
|
||||
application.register_blueprint(registry, url_prefix='/v1')
|
||||
application.register_blueprint(verbs, url_prefix='/c1')
|
||||
application.register_blueprint(api_bp, url_prefix='/api')
|
||||
application.register_blueprint(webhooks, url_prefix='/webhooks')
|
||||
application.register_blueprint(realtime, url_prefix='/realtime')
|
||||
|
||||
class RequestWithId(Request):
|
||||
request_gen = staticmethod(urn_generator(['request']))
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
super(RequestWithId, self).__init__(*args, **kwargs)
|
||||
self.request_id = self.request_gen()
|
||||
|
||||
@application.before_request
|
||||
def _request_start():
|
||||
profile.debug('Starting request: %s', request.path)
|
||||
|
||||
|
||||
@application.after_request
|
||||
def _request_end(r):
|
||||
profile.debug('Ending request: %s', request.path)
|
||||
return r
|
||||
|
||||
class InjectingFilter(logging.Filter):
|
||||
def filter(self, record):
|
||||
record.msg = '[%s] %s' % (request.request_id, record.msg)
|
||||
return True
|
||||
|
||||
profile.addFilter(InjectingFilter())
|
||||
|
||||
def close_db(exc):
|
||||
db = model_db
|
||||
if not db.is_closed():
|
||||
logger.debug('Disconnecting from database.')
|
||||
db.close()
|
||||
|
||||
if read_slave.obj is not None and not read_slave.is_closed():
|
||||
logger.debug('Disconnecting from read slave.')
|
||||
read_slave.close()
|
||||
|
||||
application.teardown_request(close_db)
|
||||
application.request_class = RequestWithId
|
||||
|
||||
if __name__ == '__main__':
|
||||
logging.config.fileConfig('conf/logging.conf', disable_existing_loggers=False)
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
bind = 'unix:/tmp/gunicorn.sock'
|
||||
workers = 16
|
||||
bind = 'unix:/tmp/gunicorn_registry.sock'
|
||||
workers = 8
|
||||
worker_class = 'gevent'
|
||||
timeout = 2000
|
||||
logconfig = 'conf/logging.conf'
|
6
conf/gunicorn_verbs.py
Normal file
6
conf/gunicorn_verbs.py
Normal file
|
@ -0,0 +1,6 @@
|
|||
bind = 'unix:/tmp/gunicorn_verbs.sock'
|
||||
workers = 4
|
||||
timeout = 2000
|
||||
logconfig = 'conf/logging.conf'
|
||||
pythonpath = '.'
|
||||
preload_app = True
|
7
conf/gunicorn_web.py
Normal file
7
conf/gunicorn_web.py
Normal file
|
@ -0,0 +1,7 @@
|
|||
bind = 'unix:/tmp/gunicorn_web.sock'
|
||||
workers = 2
|
||||
worker_class = 'gevent'
|
||||
timeout = 30
|
||||
logconfig = 'conf/logging.conf'
|
||||
pythonpath = '.'
|
||||
preload_app = True
|
|
@ -14,8 +14,12 @@ gzip_types text/plain text/xml text/css
|
|||
text/javascript application/x-javascript
|
||||
application/octet-stream;
|
||||
|
||||
upstream app_server {
|
||||
server unix:/tmp/gunicorn.sock fail_timeout=0;
|
||||
# For a TCP configuration:
|
||||
# server 192.168.0.7:8000 fail_timeout=0;
|
||||
upstream web_app_server {
|
||||
server unix:/tmp/gunicorn_web.sock fail_timeout=0;
|
||||
}
|
||||
upstream verbs_app_server {
|
||||
server unix:/tmp/gunicorn_verbs.sock fail_timeout=0;
|
||||
}
|
||||
upstream registry_app_server {
|
||||
server unix:/tmp/gunicorn_registry.sock fail_timeout=0;
|
||||
}
|
||||
|
|
|
@ -1,2 +0,0 @@
|
|||
#!/bin/sh
|
||||
exec svlogd /var/log/gunicorn/
|
|
@ -1,8 +0,0 @@
|
|||
#! /bin/bash
|
||||
|
||||
echo 'Starting gunicon'
|
||||
|
||||
cd /
|
||||
venv/bin/gunicorn -c conf/gunicorn_config.py application:application
|
||||
|
||||
echo 'Gunicorn exited'
|
2
conf/init/gunicorn_registry/log/run
Executable file
2
conf/init/gunicorn_registry/log/run
Executable file
|
@ -0,0 +1,2 @@
|
|||
#!/bin/sh
|
||||
exec svlogd /var/log/gunicorn_registry/
|
8
conf/init/gunicorn_registry/run
Executable file
8
conf/init/gunicorn_registry/run
Executable file
|
@ -0,0 +1,8 @@
|
|||
#! /bin/bash
|
||||
|
||||
echo 'Starting gunicon'
|
||||
|
||||
cd /
|
||||
venv/bin/gunicorn -c conf/gunicorn_registry.py registry:application
|
||||
|
||||
echo 'Gunicorn exited'
|
2
conf/init/gunicorn_verbs/log/run
Executable file
2
conf/init/gunicorn_verbs/log/run
Executable file
|
@ -0,0 +1,2 @@
|
|||
#!/bin/sh
|
||||
exec svlogd /var/log/gunicorn_verbs/
|
8
conf/init/gunicorn_verbs/run
Executable file
8
conf/init/gunicorn_verbs/run
Executable file
|
@ -0,0 +1,8 @@
|
|||
#! /bin/bash
|
||||
|
||||
echo 'Starting gunicon'
|
||||
|
||||
cd /
|
||||
nice -10 venv/bin/gunicorn -c conf/gunicorn_verbs.py verbs:application
|
||||
|
||||
echo 'Gunicorn exited'
|
2
conf/init/gunicorn_web/log/run
Executable file
2
conf/init/gunicorn_web/log/run
Executable file
|
@ -0,0 +1,2 @@
|
|||
#!/bin/sh
|
||||
exec svlogd /var/log/gunicorn_web/
|
8
conf/init/gunicorn_web/run
Executable file
8
conf/init/gunicorn_web/run
Executable file
|
@ -0,0 +1,8 @@
|
|||
#! /bin/bash
|
||||
|
||||
echo 'Starting gunicon'
|
||||
|
||||
cd /
|
||||
venv/bin/gunicorn -c conf/gunicorn_web.py web:application
|
||||
|
||||
echo 'Gunicorn exited'
|
|
@ -1,5 +1,5 @@
|
|||
[loggers]
|
||||
keys=root, gunicorn.error, gunicorn.access, application.profiler
|
||||
keys=root, gunicorn.error, gunicorn.access, application.profiler, boto, werkzeug
|
||||
|
||||
[handlers]
|
||||
keys=console
|
||||
|
@ -17,6 +17,18 @@ qualname=application.profiler
|
|||
level=DEBUG
|
||||
handlers=console
|
||||
|
||||
[logger_boto]
|
||||
level=INFO
|
||||
handlers=console
|
||||
propagate=0
|
||||
qualname=boto
|
||||
|
||||
[logger_werkzeug]
|
||||
level=DEBUG
|
||||
handlers=console
|
||||
propagate=0
|
||||
qualname=werkzeug
|
||||
|
||||
[logger_gunicorn.error]
|
||||
level=INFO
|
||||
handlers=console
|
||||
|
|
|
@ -1,4 +1,3 @@
|
|||
client_max_body_size 20G;
|
||||
client_body_temp_path /var/log/nginx/client_body 1 2;
|
||||
server_name _;
|
||||
|
||||
|
@ -11,17 +10,41 @@ if ($args ~ "_escaped_fragment_") {
|
|||
rewrite ^ /snapshot$uri;
|
||||
}
|
||||
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
proxy_set_header Host $http_host;
|
||||
proxy_redirect off;
|
||||
|
||||
proxy_set_header Transfer-Encoding $http_transfer_encoding;
|
||||
|
||||
location / {
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
proxy_set_header Host $http_host;
|
||||
proxy_redirect off;
|
||||
proxy_pass http://web_app_server;
|
||||
}
|
||||
|
||||
location /realtime {
|
||||
proxy_pass http://web_app_server;
|
||||
proxy_buffering off;
|
||||
proxy_request_buffering off;
|
||||
}
|
||||
|
||||
location /v1/ {
|
||||
proxy_buffering off;
|
||||
|
||||
proxy_request_buffering off;
|
||||
proxy_set_header Transfer-Encoding $http_transfer_encoding;
|
||||
|
||||
proxy_pass http://app_server;
|
||||
proxy_pass http://registry_app_server;
|
||||
proxy_read_timeout 2000;
|
||||
proxy_temp_path /var/log/nginx/proxy_temp 1 2;
|
||||
|
||||
client_max_body_size 20G;
|
||||
}
|
||||
|
||||
location /c1/ {
|
||||
proxy_buffering off;
|
||||
|
||||
proxy_request_buffering off;
|
||||
|
||||
proxy_pass http://verbs_app_server;
|
||||
proxy_read_timeout 2000;
|
||||
proxy_temp_path /var/log/nginx/proxy_temp 1 2;
|
||||
}
|
||||
|
|
18
config.py
18
config.py
|
@ -19,7 +19,8 @@ def build_requests_session():
|
|||
CLIENT_WHITELIST = ['SERVER_HOSTNAME', 'PREFERRED_URL_SCHEME', 'GITHUB_CLIENT_ID',
|
||||
'GITHUB_LOGIN_CLIENT_ID', 'MIXPANEL_KEY', 'STRIPE_PUBLISHABLE_KEY',
|
||||
'ENTERPRISE_LOGO_URL', 'SENTRY_PUBLIC_DSN', 'AUTHENTICATION_TYPE',
|
||||
'REGISTRY_TITLE', 'REGISTRY_TITLE_SHORT', 'GOOGLE_LOGIN_CLIENT_ID']
|
||||
'REGISTRY_TITLE', 'REGISTRY_TITLE_SHORT', 'GOOGLE_LOGIN_CLIENT_ID',
|
||||
'CONTACT_INFO']
|
||||
|
||||
|
||||
def getFrontendVisibleConfig(config_dict):
|
||||
|
@ -48,6 +49,12 @@ class DefaultConfig(object):
|
|||
|
||||
REGISTRY_TITLE = 'Quay.io'
|
||||
REGISTRY_TITLE_SHORT = 'Quay.io'
|
||||
CONTACT_INFO = [
|
||||
'mailto:support@quay.io',
|
||||
'irc://chat.freenode.net:6665/quayio',
|
||||
'tel:+1-888-930-3475',
|
||||
'https://twitter.com/quayio',
|
||||
]
|
||||
|
||||
# Mail config
|
||||
MAIL_SERVER = ''
|
||||
|
@ -55,7 +62,7 @@ class DefaultConfig(object):
|
|||
MAIL_PORT = 587
|
||||
MAIL_USERNAME = ''
|
||||
MAIL_PASSWORD = ''
|
||||
DEFAULT_MAIL_SENDER = ''
|
||||
MAIL_DEFAULT_SENDER = 'support@quay.io'
|
||||
MAIL_FAIL_SILENTLY = False
|
||||
TESTING = True
|
||||
|
||||
|
@ -80,11 +87,11 @@ class DefaultConfig(object):
|
|||
AUTHENTICATION_TYPE = 'Database'
|
||||
|
||||
# Build logs
|
||||
BUILDLOGS_REDIS = {'host': 'logs.quay.io'}
|
||||
BUILDLOGS_REDIS = {'host': 'localhost'}
|
||||
BUILDLOGS_OPTIONS = []
|
||||
|
||||
# Real-time user events
|
||||
USER_EVENTS_REDIS = {'host': 'logs.quay.io'}
|
||||
USER_EVENTS_REDIS = {'host': 'localhost'}
|
||||
|
||||
# Stripe config
|
||||
BILLING_TYPE = 'FakeStripe'
|
||||
|
@ -132,9 +139,6 @@ class DefaultConfig(object):
|
|||
DIFFS_QUEUE_NAME = 'imagediff'
|
||||
DOCKERFILE_BUILD_QUEUE_NAME = 'dockerfilebuild'
|
||||
|
||||
# TODO: Remove this in the prod push following the notifications change.
|
||||
WEBHOOK_QUEUE_NAME = 'webhook'
|
||||
|
||||
# Super user config. Note: This MUST BE an empty list for the default config.
|
||||
SUPER_USERS = []
|
||||
|
||||
|
|
|
@ -7,9 +7,9 @@ from datetime import datetime
|
|||
from peewee import *
|
||||
from data.read_slave import ReadSlaveModel
|
||||
from sqlalchemy.engine.url import make_url
|
||||
from urlparse import urlparse
|
||||
from util.names import urn_generator
|
||||
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
|
@ -80,6 +80,16 @@ def uuid_generator():
|
|||
return str(uuid.uuid4())
|
||||
|
||||
|
||||
def close_db_filter(_):
|
||||
if not db.is_closed():
|
||||
logger.debug('Disconnecting from database.')
|
||||
db.close()
|
||||
|
||||
if read_slave.obj is not None and not read_slave.is_closed():
|
||||
logger.debug('Disconnecting from read slave.')
|
||||
read_slave.close()
|
||||
|
||||
|
||||
class BaseModel(ReadSlaveModel):
|
||||
class Meta:
|
||||
database = db
|
||||
|
|
|
@ -21,6 +21,10 @@ def upgrade(tables):
|
|||
sa.PrimaryKeyConstraint('id', name=op.f('pk_imagestoragetransformation'))
|
||||
)
|
||||
op.create_index('imagestoragetransformation_name', 'imagestoragetransformation', ['name'], unique=True)
|
||||
op.bulk_insert(tables.imagestoragetransformation,
|
||||
[
|
||||
{'id':1, 'name':'squash'},
|
||||
])
|
||||
op.create_table('derivedimagestorage',
|
||||
sa.Column('id', sa.Integer(), nullable=False),
|
||||
sa.Column('source_id', sa.Integer(), nullable=True),
|
||||
|
|
|
@ -13,7 +13,8 @@ from data.database import (User, Repository, Image, AccessToken, Role, Repositor
|
|||
Notification, ImageStorageLocation, ImageStoragePlacement,
|
||||
ExternalNotificationEvent, ExternalNotificationMethod,
|
||||
RepositoryNotification, RepositoryAuthorizedEmail, TeamMemberInvite,
|
||||
DerivedImageStorage, random_string_generator, db, BUILD_PHASE)
|
||||
DerivedImageStorage, ImageStorageTransformation, random_string_generator,
|
||||
db, BUILD_PHASE)
|
||||
from peewee import JOIN_LEFT_OUTER, fn
|
||||
from util.validation import (validate_username, validate_email, validate_password,
|
||||
INVALID_PASSWORD_MESSAGE)
|
||||
|
@ -578,6 +579,13 @@ def get_user(username):
|
|||
return None
|
||||
|
||||
|
||||
def get_namespace_user(username):
|
||||
try:
|
||||
return User.get(User.username == username)
|
||||
except User.DoesNotExist:
|
||||
return None
|
||||
|
||||
|
||||
def get_user_or_org(username):
|
||||
try:
|
||||
return User.get(User.username == username, User.robot == False)
|
||||
|
@ -1247,6 +1255,20 @@ def find_or_create_derived_storage(source, transformation_name, preferred_locati
|
|||
return new_storage
|
||||
|
||||
|
||||
def delete_derived_storage_by_uuid(storage_uuid):
|
||||
try:
|
||||
image_storage = get_storage_by_uuid(storage_uuid)
|
||||
except InvalidImageException:
|
||||
return
|
||||
|
||||
try:
|
||||
DerivedImageStorage.get(derivative=image_storage)
|
||||
except DerivedImageStorage.DoesNotExist:
|
||||
return
|
||||
|
||||
image_storage.delete_instance(recursive=True)
|
||||
|
||||
|
||||
def get_storage_by_uuid(storage_uuid):
|
||||
placements = list(ImageStoragePlacement
|
||||
.select(ImageStoragePlacement, ImageStorage, ImageStorageLocation)
|
||||
|
@ -1305,7 +1327,15 @@ def set_image_metadata(docker_image_id, namespace_name, repository_name, created
|
|||
|
||||
# We cleanup any old checksum in case it's a retry after a fail
|
||||
fetched.storage.checksum = None
|
||||
fetched.storage.created = dateutil.parser.parse(created_date_str).replace(tzinfo=None)
|
||||
fetched.storage.created = datetime.now()
|
||||
|
||||
if created_date_str is not None:
|
||||
try:
|
||||
fetched.storage.created = dateutil.parser.parse(created_date_str).replace(tzinfo=None)
|
||||
except:
|
||||
# parse raises different exceptions, so we cannot use a specific kind of handler here.
|
||||
pass
|
||||
|
||||
fetched.storage.comment = comment
|
||||
fetched.storage.command = command
|
||||
|
||||
|
@ -1390,48 +1420,87 @@ def garbage_collect_repository(namespace_name, repository_name):
|
|||
all_images = {int(img.id): img for img in all_repo_images}
|
||||
to_remove = set(all_images.keys()).difference(referenced_anscestors)
|
||||
|
||||
logger.info('Cleaning up unreferenced images: %s', to_remove)
|
||||
if len(to_remove) > 0:
|
||||
logger.info('Cleaning up unreferenced images: %s', to_remove)
|
||||
storage_id_whitelist = {all_images[to_remove_id].storage.id for to_remove_id in to_remove}
|
||||
|
||||
uuids_to_check_for_gc = set()
|
||||
for image_id_to_remove in to_remove:
|
||||
image_to_remove = all_images[image_id_to_remove]
|
||||
Image.delete().where(Image.id << list(to_remove)).execute()
|
||||
|
||||
logger.debug('Adding image storage to the gc list: %s',
|
||||
image_to_remove.storage.uuid)
|
||||
uuids_to_check_for_gc.add(image_to_remove.storage.uuid)
|
||||
garbage_collect_storage(storage_id_whitelist)
|
||||
|
||||
image_to_remove.delete_instance()
|
||||
return len(to_remove)
|
||||
|
||||
def remove_storages(query):
|
||||
for storage in query:
|
||||
logger.debug('Garbage collecting image storage: %s', storage.uuid)
|
||||
|
||||
image_path = config.store.image_path(storage.uuid)
|
||||
for placement in storage.imagestorageplacement_set:
|
||||
location_name = placement.location.name
|
||||
placement.delete_instance()
|
||||
config.store.remove({location_name}, image_path)
|
||||
def garbage_collect_storage(storage_id_whitelist):
|
||||
# We are going to make the conscious decision to not delete image storage inside the transaction
|
||||
# This may end up producing garbage in s3, trading off for higher availability in the database
|
||||
def placements_query_to_paths_set(placements_query):
|
||||
return {(placement.location.name, config.store.image_path(placement.storage.uuid))
|
||||
for placement in placements_query}
|
||||
|
||||
storage.delete_instance(recursive=True)
|
||||
def orphaned_storage_query(select_base_query, candidates):
|
||||
return (select_base_query
|
||||
.switch(ImageStorage)
|
||||
.join(Image, JOIN_LEFT_OUTER)
|
||||
.switch(ImageStorage)
|
||||
.join(DerivedImageStorage, JOIN_LEFT_OUTER,
|
||||
on=(ImageStorage.id == DerivedImageStorage.derivative))
|
||||
.where(ImageStorage.id << list(candidates))
|
||||
.group_by(ImageStorage)
|
||||
.having((fn.Count(Image.id) == 0) & (fn.Count(DerivedImageStorage.id) == 0)))
|
||||
|
||||
if uuids_to_check_for_gc:
|
||||
storage_to_remove = (ImageStorage
|
||||
.select()
|
||||
.join(Image, JOIN_LEFT_OUTER)
|
||||
.group_by(ImageStorage)
|
||||
.where(ImageStorage.uuid << list(uuids_to_check_for_gc))
|
||||
.having(fn.Count(Image.id) == 0))
|
||||
logger.debug('Garbage collecting storage from candidates: %s', storage_id_whitelist)
|
||||
with config.app_config['DB_TRANSACTION_FACTORY'](db):
|
||||
# Find out which derived storages will be removed, and add them to the whitelist
|
||||
orphaned_from_candidates = list(orphaned_storage_query(ImageStorage.select(ImageStorage.id),
|
||||
storage_id_whitelist))
|
||||
|
||||
remove_storages(storage_to_remove)
|
||||
if len(orphaned_from_candidates) > 0:
|
||||
derived_to_remove = (ImageStorage
|
||||
.select(ImageStorage.id)
|
||||
.join(DerivedImageStorage,
|
||||
on=(ImageStorage.id == DerivedImageStorage.derivative))
|
||||
.where(DerivedImageStorage.source << orphaned_from_candidates))
|
||||
storage_id_whitelist.update({derived.id for derived in derived_to_remove})
|
||||
|
||||
# Now remove any derived image storages whose sources have been removed
|
||||
derived_storages_to_remove = (ImageStorage
|
||||
.select()
|
||||
.join(DerivedImageStorage, on=(ImageStorage.id == DerivedImageStorage.derivative))
|
||||
.where(DerivedImageStorage.source >> None))
|
||||
remove_storages(derived_storages_to_remove)
|
||||
# Remove the dervived image storages with sources of orphaned storages
|
||||
(DerivedImageStorage
|
||||
.delete()
|
||||
.where(DerivedImageStorage.source << orphaned_from_candidates)
|
||||
.execute())
|
||||
|
||||
return len(to_remove)
|
||||
# Track all of the data that should be removed from blob storage
|
||||
placements_to_remove = orphaned_storage_query(ImageStoragePlacement
|
||||
.select(ImageStoragePlacement,
|
||||
ImageStorage,
|
||||
ImageStorageLocation)
|
||||
.join(ImageStorageLocation)
|
||||
.switch(ImageStoragePlacement)
|
||||
.join(ImageStorage),
|
||||
storage_id_whitelist)
|
||||
paths_to_remove = placements_query_to_paths_set(placements_to_remove.clone())
|
||||
|
||||
# Remove the placements for orphaned storages
|
||||
placements_subquery = list(placements_to_remove.clone().select(ImageStoragePlacement.id))
|
||||
if len(placements_subquery) > 0:
|
||||
(ImageStoragePlacement
|
||||
.delete()
|
||||
.where(ImageStoragePlacement.id << list(placements_subquery))
|
||||
.execute())
|
||||
|
||||
# Remove the all orphaned storages
|
||||
orphaned_storages = list(orphaned_storage_query(ImageStorage.select(ImageStorage.id),
|
||||
storage_id_whitelist))
|
||||
if len(orphaned_storages) > 0:
|
||||
(ImageStorage
|
||||
.delete()
|
||||
.where(ImageStorage.id << orphaned_storages)
|
||||
.execute())
|
||||
|
||||
# Delete the actual blob storage
|
||||
for location_name, image_path in paths_to_remove:
|
||||
logger.debug('Removing %s from %s', image_path, location_name)
|
||||
config.store.remove({location_name}, image_path)
|
||||
|
||||
|
||||
def get_tag_image(namespace_name, repository_name, tag_name):
|
||||
|
|
|
@ -30,7 +30,7 @@ class UserEventsBuilderModule(object):
|
|||
if not redis_config:
|
||||
# This is the old key name.
|
||||
redis_config = {
|
||||
'host': app.config.get('USER_EVENTS_REDIS_HOSTNAME')
|
||||
'host': app.config.get('USER_EVENTS_REDIS_HOSTNAME'),
|
||||
}
|
||||
|
||||
user_events = UserEventBuilder(redis_config)
|
||||
|
@ -45,7 +45,7 @@ class UserEventsBuilderModule(object):
|
|||
|
||||
|
||||
class UserEvent(object):
|
||||
"""
|
||||
"""
|
||||
Defines a helper class for publishing to realtime user events
|
||||
as backed by Redis.
|
||||
"""
|
||||
|
@ -74,7 +74,7 @@ class UserEvent(object):
|
|||
thread = threading.Thread(target=conduct)
|
||||
thread.start()
|
||||
|
||||
|
||||
|
||||
class UserEventListener(object):
|
||||
"""
|
||||
Defines a helper class for subscribing to realtime user events as
|
||||
|
@ -90,7 +90,7 @@ class UserEventListener(object):
|
|||
@staticmethod
|
||||
def _user_event_key(username, event_id):
|
||||
return 'user/%s/events/%s' % (username, event_id)
|
||||
|
||||
|
||||
def event_stream(self):
|
||||
"""
|
||||
Starts listening for events on the channel(s), yielding for each event
|
||||
|
|
|
@ -317,7 +317,7 @@ class BuildTriggerAnalyze(RepositoryParamResource):
|
|||
if not found_repository:
|
||||
return {
|
||||
'status': 'error',
|
||||
'message': 'Repository "%s" was not found' % (base_image)
|
||||
'message': 'Repository "%s" referenced by the Dockerfile was not found' % (base_image)
|
||||
}
|
||||
|
||||
# If the repository is private and the user cannot see that repo, then
|
||||
|
@ -326,7 +326,7 @@ class BuildTriggerAnalyze(RepositoryParamResource):
|
|||
if found_repository.visibility.name != 'public' and not can_read:
|
||||
return {
|
||||
'status': 'error',
|
||||
'message': 'Repository "%s" was not found' % (base_image)
|
||||
'message': 'Repository "%s" referenced by the Dockerfile was not found' % (base_image)
|
||||
}
|
||||
|
||||
# Check to see if the repository is public. If not, we suggest the
|
||||
|
@ -450,18 +450,18 @@ class BuildTriggerFieldValues(RepositoryParamResource):
|
|||
""" Custom verb to fetch a values list for a particular field name. """
|
||||
@require_repo_admin
|
||||
@nickname('listTriggerFieldValues')
|
||||
def get(self, namespace, repository, trigger_uuid, field_name):
|
||||
def post(self, namespace, repository, trigger_uuid, field_name):
|
||||
""" List the field values for a custom run field. """
|
||||
try:
|
||||
trigger = model.get_build_trigger(namespace, repository, trigger_uuid)
|
||||
except model.InvalidBuildTriggerException:
|
||||
raise NotFound()
|
||||
|
||||
config = request.get_json() or json.loads(trigger.config)
|
||||
user_permission = UserAdminPermission(trigger.connected_user.username)
|
||||
if user_permission.can():
|
||||
trigger_handler = BuildTriggerBase.get_trigger_for_service(trigger.service.name)
|
||||
values = trigger_handler.list_field_values(trigger.auth_token, json.loads(trigger.config),
|
||||
field_name)
|
||||
values = trigger_handler.list_field_values(trigger.auth_token, config, field_name)
|
||||
|
||||
if values is None:
|
||||
raise NotFound()
|
||||
|
|
|
@ -106,7 +106,15 @@ def conduct_oauth_login(service_name, user_id, username, email, metadata={}):
|
|||
logger.debug('Aliasing with state: %s' % state)
|
||||
analytics.alias(to_login.username, state)
|
||||
|
||||
except model.DataModelException, ex:
|
||||
except model.InvalidEmailAddressException as ieex:
|
||||
message = "The e-mail address %s is already associated " % (email, )
|
||||
message = message + "with an existing %s account." % (app.config['REGISTRY_TITLE_SHORT'], )
|
||||
message = message + "\nPlease log in with your username and password and "
|
||||
message = message + "associate your %s account to use it in the future." % (service_name, )
|
||||
|
||||
return render_ologin_error(service_name, message)
|
||||
|
||||
except model.DataModelException as ex:
|
||||
return render_ologin_error(service_name, ex.message)
|
||||
|
||||
if common_login(to_login):
|
||||
|
|
|
@ -10,6 +10,7 @@ from flask.ext.principal import identity_changed
|
|||
from random import SystemRandom
|
||||
|
||||
from data import model
|
||||
from data.database import db
|
||||
from app import app, login_manager, dockerfile_build_queue, notification_queue
|
||||
from auth.permissions import QuayDeferredPermissionUser
|
||||
from auth import scopes
|
||||
|
@ -170,6 +171,10 @@ def render_page_template(name, **kwargs):
|
|||
external_styles = get_external_css(local=not app.config.get('USE_CDN', True))
|
||||
external_scripts = get_external_javascript(local=not app.config.get('USE_CDN', True))
|
||||
|
||||
contact_href = None
|
||||
if len(app.config.get('CONTACT_INFO', [])) == 1:
|
||||
contact_href = app.config['CONTACT_INFO'][0]
|
||||
|
||||
resp = make_response(render_template(name, route_data=json.dumps(get_route_data()),
|
||||
external_styles=external_styles,
|
||||
external_scripts=external_scripts,
|
||||
|
@ -186,6 +191,7 @@ def render_page_template(name, **kwargs):
|
|||
show_chat=features.OLARK_CHAT,
|
||||
cache_buster=cache_buster,
|
||||
has_billing=features.BILLING,
|
||||
contact_href=contact_href,
|
||||
**kwargs))
|
||||
|
||||
resp.headers['X-FRAME-OPTIONS'] = 'DENY'
|
||||
|
@ -217,14 +223,15 @@ def start_build(repository, dockerfile_id, tags, build_name, subdir, manual,
|
|||
'build_subdir': subdir
|
||||
}
|
||||
|
||||
build_request = model.create_repository_build(repository, token, job_config,
|
||||
dockerfile_id, build_name,
|
||||
trigger, pull_robot_name=pull_robot_name)
|
||||
with app.config['DB_TRANSACTION_FACTORY'](db):
|
||||
build_request = model.create_repository_build(repository, token, job_config,
|
||||
dockerfile_id, build_name,
|
||||
trigger, pull_robot_name=pull_robot_name)
|
||||
|
||||
dockerfile_build_queue.put([str(repository.namespace_user.id), repository.name], json.dumps({
|
||||
'build_uuid': build_request.uuid,
|
||||
'pull_credentials': model.get_pull_credentials(pull_robot_name) if pull_robot_name else None
|
||||
}), retries_remaining=1)
|
||||
dockerfile_build_queue.put([str(repository.namespace_user.id), repository.name], json.dumps({
|
||||
'build_uuid': build_request.uuid,
|
||||
'pull_credentials': model.get_pull_credentials(pull_robot_name) if pull_robot_name else None
|
||||
}), retries_remaining=1)
|
||||
|
||||
# Add the build to the repo's log.
|
||||
metadata = {
|
||||
|
|
|
@ -70,7 +70,7 @@ def create_user():
|
|||
abort(400, 'User creation is disabled. Please speak to your administrator.')
|
||||
|
||||
user_data = request.get_json()
|
||||
if not 'username' in user_data:
|
||||
if not user_data or not 'username' in user_data:
|
||||
abort(400, 'Missing username')
|
||||
|
||||
username = user_data['username']
|
||||
|
@ -299,13 +299,6 @@ def update_images(namespace, repository):
|
|||
# Make sure the repo actually exists.
|
||||
abort(404, message='Unknown repository', issue='unknown-repo')
|
||||
|
||||
profile.debug('Parsing image data')
|
||||
image_with_checksums = json.loads(request.data.decode('utf8'))
|
||||
|
||||
updated_tags = {}
|
||||
for image in image_with_checksums:
|
||||
updated_tags[image['Tag']] = image['id']
|
||||
|
||||
if get_authenticated_user():
|
||||
profile.debug('Publishing push event')
|
||||
username = get_authenticated_user().username
|
||||
|
@ -326,12 +319,11 @@ def update_images(namespace, repository):
|
|||
# Generate a job for each notification that has been added to this repo
|
||||
profile.debug('Adding notifications for repository')
|
||||
|
||||
updated_tags = session.get('pushed_tags', {})
|
||||
event_data = {
|
||||
'updated_tags': updated_tags,
|
||||
'pushed_image_count': len(image_with_checksums),
|
||||
'pruned_image_count': num_removed
|
||||
}
|
||||
|
||||
spawn_notification(repo, 'repo_push', event_data)
|
||||
return make_response('Updated', 204)
|
||||
|
||||
|
|
|
@ -1,7 +1,9 @@
|
|||
import logging
|
||||
|
||||
from notificationhelper import build_event_data
|
||||
from util.jinjautil import get_template_env
|
||||
|
||||
template_env = get_template_env("events")
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
class InvalidNotificationEventException(Exception):
|
||||
|
@ -14,7 +16,7 @@ class NotificationEvent(object):
|
|||
def get_level(self, event_data, notification_data):
|
||||
"""
|
||||
Returns a 'level' representing the severity of the event.
|
||||
Valid values are: 'info', 'warning', 'error', 'primary'
|
||||
Valid values are: 'info', 'warning', 'error', 'primary', 'success'
|
||||
"""
|
||||
raise NotImplementedError
|
||||
|
||||
|
@ -28,7 +30,10 @@ class NotificationEvent(object):
|
|||
"""
|
||||
Returns a human readable HTML message for the given notification data.
|
||||
"""
|
||||
raise NotImplementedError
|
||||
return template_env.get_template(self.event_name() + '.html').render({
|
||||
'event_data': event_data,
|
||||
'notification_data': notification_data
|
||||
})
|
||||
|
||||
def get_sample_data(self, repository=None):
|
||||
"""
|
||||
|
@ -59,32 +64,14 @@ class RepoPushEvent(NotificationEvent):
|
|||
return 'repo_push'
|
||||
|
||||
def get_level(self, event_data, notification_data):
|
||||
return 'info'
|
||||
return 'primary'
|
||||
|
||||
def get_summary(self, event_data, notification_data):
|
||||
return 'Repository %s updated' % (event_data['repository'])
|
||||
|
||||
def get_message(self, event_data, notification_data):
|
||||
if not event_data.get('updated_tags', {}).keys():
|
||||
html = """
|
||||
Repository <a href="%s">%s</a> has been updated via a push.
|
||||
""" % (event_data['homepage'],
|
||||
event_data['repository'])
|
||||
else:
|
||||
html = """
|
||||
Repository <a href="%s">%s</a> has been updated via a push.
|
||||
<br><br>
|
||||
Tags Updated: %s
|
||||
""" % (event_data['homepage'],
|
||||
event_data['repository'],
|
||||
', '.join(event_data['updated_tags'].keys()))
|
||||
|
||||
return html
|
||||
|
||||
def get_sample_data(self, repository):
|
||||
return build_event_data(repository, {
|
||||
'updated_tags': {'latest': 'someimageid', 'foo': 'anotherimage'},
|
||||
'pushed_image_count': 10,
|
||||
'pruned_image_count': 3
|
||||
})
|
||||
|
||||
|
@ -109,26 +96,7 @@ class BuildQueueEvent(NotificationEvent):
|
|||
}, subpage='/build?current=%s' % build_uuid)
|
||||
|
||||
def get_summary(self, event_data, notification_data):
|
||||
return 'Build queued for repository %s' % (event_data['repository'])
|
||||
|
||||
def get_message(self, event_data, notification_data):
|
||||
is_manual = event_data['is_manual']
|
||||
if is_manual:
|
||||
html = """
|
||||
A <a href="%s">new build</a> has been manually queued to start on repository %s.
|
||||
<br><br>
|
||||
Build ID: %s
|
||||
""" % (event_data['homepage'], event_data['repository'], event_data['build_id'])
|
||||
else:
|
||||
html = """
|
||||
A <a href="%s">new build</a> has been queued via a %s trigger to start on repository %s.
|
||||
<br><br>
|
||||
Build ID: %s
|
||||
""" % (event_data['homepage'], event_data['trigger_kind'],
|
||||
event_data['repository'], event_data['build_id'])
|
||||
|
||||
return html
|
||||
|
||||
return 'Build queued for repository %s' % (event_data['repository'])
|
||||
|
||||
|
||||
class BuildStartEvent(NotificationEvent):
|
||||
|
@ -152,15 +120,6 @@ class BuildStartEvent(NotificationEvent):
|
|||
def get_summary(self, event_data, notification_data):
|
||||
return 'Build started for repository %s' % (event_data['repository'])
|
||||
|
||||
def get_message(self, event_data, notification_data):
|
||||
html = """
|
||||
A <a href="%s">new build</a> has started on repository %s.
|
||||
<br><br>
|
||||
Build ID: %s
|
||||
""" % (event_data['homepage'], event_data['repository'], event_data['build_id'])
|
||||
|
||||
return html
|
||||
|
||||
|
||||
class BuildSuccessEvent(NotificationEvent):
|
||||
@classmethod
|
||||
|
@ -168,7 +127,7 @@ class BuildSuccessEvent(NotificationEvent):
|
|||
return 'build_success'
|
||||
|
||||
def get_level(self, event_data, notification_data):
|
||||
return 'primary'
|
||||
return 'success'
|
||||
|
||||
def get_sample_data(self, repository):
|
||||
build_uuid = 'fake-build-id'
|
||||
|
@ -183,15 +142,6 @@ class BuildSuccessEvent(NotificationEvent):
|
|||
def get_summary(self, event_data, notification_data):
|
||||
return 'Build succeeded for repository %s' % (event_data['repository'])
|
||||
|
||||
def get_message(self, event_data, notification_data):
|
||||
html = """
|
||||
A <a href="%s">build</a> has finished on repository %s.
|
||||
<br><br>
|
||||
Build ID: %s
|
||||
""" % (event_data['homepage'], event_data['repository'], event_data['build_id'])
|
||||
|
||||
return html
|
||||
|
||||
|
||||
class BuildFailureEvent(NotificationEvent):
|
||||
@classmethod
|
||||
|
@ -215,13 +165,3 @@ class BuildFailureEvent(NotificationEvent):
|
|||
def get_summary(self, event_data, notification_data):
|
||||
return 'Build failure for repository %s' % (event_data['repository'])
|
||||
|
||||
def get_message(self, event_data, notification_data):
|
||||
html = """
|
||||
A <a href="%s">build</a> has failed on repository %s.
|
||||
<br><br>
|
||||
Reason: %s<br>
|
||||
Build ID: %s<br>
|
||||
""" % (event_data['homepage'], event_data['repository'],
|
||||
event_data['error_message'], event_data['build_id'])
|
||||
|
||||
return html
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
from app import app, notification_queue
|
||||
from data import model
|
||||
from auth.auth_context import get_authenticated_user, get_validated_oauth_token
|
||||
|
||||
import json
|
||||
|
||||
|
@ -27,19 +28,35 @@ def build_event_data(repo, extra_data={}, subpage=None):
|
|||
event_data.update(extra_data)
|
||||
return event_data
|
||||
|
||||
def build_notification_data(notification, event_data):
|
||||
def build_notification_data(notification, event_data, performer_data=None):
|
||||
if not performer_data:
|
||||
performer_data = {}
|
||||
|
||||
oauth_token = get_validated_oauth_token()
|
||||
if oauth_token:
|
||||
performer_data['oauth_token_id'] = oauth_token.id
|
||||
performer_data['oauth_token_application_id'] = oauth_token.application.client_id
|
||||
performer_data['oauth_token_application'] = oauth_token.application.name
|
||||
|
||||
performer_user = get_authenticated_user()
|
||||
if performer_user:
|
||||
performer_data['entity_id'] = performer_user.id
|
||||
performer_data['entity_name'] = performer_user.username
|
||||
|
||||
return {
|
||||
'notification_uuid': notification.uuid,
|
||||
'event_data': event_data
|
||||
'event_data': event_data,
|
||||
'performer_data': performer_data,
|
||||
}
|
||||
|
||||
|
||||
def spawn_notification(repo, event_name, extra_data={}, subpage=None, pathargs=[]):
|
||||
def spawn_notification(repo, event_name, extra_data={}, subpage=None, pathargs=[],
|
||||
performer_data=None):
|
||||
event_data = build_event_data(repo, extra_data=extra_data, subpage=subpage)
|
||||
|
||||
notifications = model.list_repo_notifications(repo.namespace_user.username, repo.name,
|
||||
event_name=event_name)
|
||||
for notification in notifications:
|
||||
notification_data = build_notification_data(notification, event_data)
|
||||
for notification in list(notifications):
|
||||
notification_data = build_notification_data(notification, event_data, performer_data)
|
||||
path = [str(repo.namespace_user.id), repo.name, event_name] + pathargs
|
||||
notification_queue.put(path, json.dumps(notification_data))
|
||||
|
|
|
@ -211,7 +211,7 @@ class FlowdockMethod(NotificationMethod):
|
|||
if not token:
|
||||
return
|
||||
|
||||
owner = model.get_user(notification.repository.namespace_user.username)
|
||||
owner = model.get_user_or_org(notification.repository.namespace_user.username)
|
||||
if not owner:
|
||||
# Something went wrong.
|
||||
return
|
||||
|
@ -267,7 +267,7 @@ class HipchatMethod(NotificationMethod):
|
|||
if not token or not room_id:
|
||||
return
|
||||
|
||||
owner = model.get_user(notification.repository.namespace_user.username)
|
||||
owner = model.get_user_or_org(notification.repository.namespace_user.username)
|
||||
if not owner:
|
||||
# Something went wrong.
|
||||
return
|
||||
|
@ -279,6 +279,7 @@ class HipchatMethod(NotificationMethod):
|
|||
'info': 'gray',
|
||||
'warning': 'yellow',
|
||||
'error': 'red',
|
||||
'success': 'green',
|
||||
'primary': 'purple'
|
||||
}.get(level, 'gray')
|
||||
|
||||
|
@ -303,6 +304,56 @@ class HipchatMethod(NotificationMethod):
|
|||
raise NotificationMethodPerformException(ex.message)
|
||||
|
||||
|
||||
from HTMLParser import HTMLParser
|
||||
|
||||
class SlackAdjuster(HTMLParser):
|
||||
def __init__(self):
|
||||
self.reset()
|
||||
self.result = []
|
||||
|
||||
def handle_data(self, d):
|
||||
self.result.append(d)
|
||||
|
||||
def get_attr(self, attrs, name):
|
||||
for attr in attrs:
|
||||
if attr[0] == name:
|
||||
return attr[1]
|
||||
|
||||
return ''
|
||||
|
||||
def handle_starttag(self, tag, attrs):
|
||||
if tag == 'a':
|
||||
self.result.append('<%s|' % (self.get_attr(attrs, 'href'), ))
|
||||
|
||||
if tag == 'i':
|
||||
self.result.append('_')
|
||||
|
||||
if tag == 'b' or tag == 'strong':
|
||||
self.result.append('*')
|
||||
|
||||
if tag == 'img':
|
||||
self.result.append(self.get_attr(attrs, 'alt'))
|
||||
self.result.append(' ')
|
||||
|
||||
def handle_endtag(self, tag):
|
||||
if tag == 'a':
|
||||
self.result.append('>')
|
||||
|
||||
if tag == 'b' or tag == 'strong':
|
||||
self.result.append('*')
|
||||
|
||||
if tag == 'i':
|
||||
self.result.append('_')
|
||||
|
||||
def get_data(self):
|
||||
return ''.join(self.result)
|
||||
|
||||
def adjust_tags(html):
|
||||
s = SlackAdjuster()
|
||||
s.feed(html)
|
||||
return s.get_data()
|
||||
|
||||
|
||||
class SlackMethod(NotificationMethod):
|
||||
""" Method for sending notifications to Slack via the API:
|
||||
https://api.slack.com/docs/attachments
|
||||
|
@ -318,12 +369,11 @@ class SlackMethod(NotificationMethod):
|
|||
if not config_data.get('subdomain', '').isalnum():
|
||||
raise CannotValidateNotificationMethodException('Missing Slack Subdomain Name')
|
||||
|
||||
def formatForSlack(self, message):
|
||||
def format_for_slack(self, message):
|
||||
message = message.replace('\n', '')
|
||||
message = re.sub(r'\s+', ' ', message)
|
||||
message = message.replace('<br>', '\n')
|
||||
message = re.sub(r'<a href="(.+)">(.+)</a>', '<\\1|\\2>', message)
|
||||
return message
|
||||
return adjust_tags(message)
|
||||
|
||||
def perform(self, notification, event_handler, notification_data):
|
||||
config_data = json.loads(notification.config_json)
|
||||
|
@ -334,7 +384,7 @@ class SlackMethod(NotificationMethod):
|
|||
if not token or not subdomain:
|
||||
return
|
||||
|
||||
owner = model.get_user(notification.repository.namespace_user.username)
|
||||
owner = model.get_user_or_org(notification.repository.namespace_user.username)
|
||||
if not owner:
|
||||
# Something went wrong.
|
||||
return
|
||||
|
@ -346,6 +396,7 @@ class SlackMethod(NotificationMethod):
|
|||
'info': '#ffffff',
|
||||
'warning': 'warning',
|
||||
'error': 'danger',
|
||||
'success': 'good',
|
||||
'primary': 'good'
|
||||
}.get(level, '#ffffff')
|
||||
|
||||
|
@ -359,8 +410,9 @@ class SlackMethod(NotificationMethod):
|
|||
'attachments': [
|
||||
{
|
||||
'fallback': summary,
|
||||
'text': self.formatForSlack(message),
|
||||
'color': color
|
||||
'text': self.format_for_slack(message),
|
||||
'color': color,
|
||||
'mrkdwn_in': ["text"]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
|
@ -197,12 +197,15 @@ def put_image_layer(namespace, repository, image_id):
|
|||
# Create a socket reader to read the input stream containing the layer data.
|
||||
sr = SocketReader(input_stream)
|
||||
|
||||
# Add a handler that store the data in storage.
|
||||
tmp, store_hndlr = store.temp_store_handler()
|
||||
sr.add_handler(store_hndlr)
|
||||
# Add a handler that copies the data into a temp file. This is used to calculate the tarsum,
|
||||
# which is only needed for older versions of Docker.
|
||||
requires_tarsum = session.get('checksum_format') == 'tarsum'
|
||||
if requires_tarsum:
|
||||
tmp, tmp_hndlr = store.temp_store_handler()
|
||||
sr.add_handler(tmp_hndlr)
|
||||
|
||||
# Add a handler to compute the uncompressed size of the layer.
|
||||
uncompressed_size_info, size_hndlr = gzipstream.calculate_size_handler()
|
||||
# Add a handler to compute the compressed and uncompressed sizes of the layer.
|
||||
size_info, size_hndlr = gzipstream.calculate_size_handler()
|
||||
sr.add_handler(size_hndlr)
|
||||
|
||||
# Add a handler which computes the checksum.
|
||||
|
@ -217,14 +220,15 @@ def put_image_layer(namespace, repository, image_id):
|
|||
csums.append('sha256:{0}'.format(h.hexdigest()))
|
||||
|
||||
try:
|
||||
image_size = tmp.tell()
|
||||
|
||||
# Save the size of the image.
|
||||
model.set_image_size(image_id, namespace, repository, image_size, uncompressed_size_info.size)
|
||||
model.set_image_size(image_id, namespace, repository, size_info.compressed_size,
|
||||
size_info.uncompressed_size)
|
||||
|
||||
if requires_tarsum:
|
||||
tmp.seek(0)
|
||||
csums.append(checksums.compute_tarsum(tmp, json_data))
|
||||
tmp.close()
|
||||
|
||||
tmp.seek(0)
|
||||
csums.append(checksums.compute_tarsum(tmp, json_data))
|
||||
tmp.close()
|
||||
except (IOError, checksums.TarError) as e:
|
||||
logger.debug('put_image_layer: Error when computing tarsum '
|
||||
'{0}'.format(e))
|
||||
|
@ -268,7 +272,19 @@ def put_image_checksum(namespace, repository, image_id):
|
|||
if not permission.can():
|
||||
abort(403)
|
||||
|
||||
checksum = request.headers.get('X-Docker-Checksum')
|
||||
# Docker Version < 0.10 (tarsum+sha):
|
||||
old_checksum = request.headers.get('X-Docker-Checksum')
|
||||
|
||||
# Docker Version >= 0.10 (sha):
|
||||
new_checksum = request.headers.get('X-Docker-Checksum-Payload')
|
||||
|
||||
# Store whether we need to calculate the tarsum.
|
||||
if new_checksum:
|
||||
session['checksum_format'] = 'sha256'
|
||||
else:
|
||||
session['checksum_format'] = 'tarsum'
|
||||
|
||||
checksum = new_checksum or old_checksum
|
||||
if not checksum:
|
||||
abort(400, "Missing checksum for image %(image_id)s", issue='missing-checksum',
|
||||
image_id=image_id)
|
||||
|
@ -279,6 +295,9 @@ def put_image_checksum(namespace, repository, image_id):
|
|||
|
||||
profile.debug('Looking up repo image')
|
||||
repo_image = model.get_repo_image(namespace, repository, image_id)
|
||||
if not repo_image or not repo_image.storage:
|
||||
abort(404, 'Image not found: %(image_id)s', issue='unknown-image', image_id=image_id)
|
||||
|
||||
uuid = repo_image.storage.uuid
|
||||
|
||||
profile.debug('Looking up repo layer data')
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
import logging
|
||||
import json
|
||||
|
||||
from flask import abort, request, jsonify, make_response, Blueprint
|
||||
from flask import abort, request, jsonify, make_response, Blueprint, session
|
||||
|
||||
from app import app
|
||||
from util.names import parse_repository_name
|
||||
|
@ -59,6 +59,12 @@ def put_tag(namespace, repository, tag):
|
|||
docker_image_id = json.loads(request.data)
|
||||
model.create_or_update_tag(namespace, repository, tag, docker_image_id)
|
||||
|
||||
# Store the updated tag.
|
||||
if not 'pushed_tags' in session:
|
||||
session['pushed_tags'] = {}
|
||||
|
||||
session['pushed_tags'][tag] = docker_image_id
|
||||
|
||||
return make_response('Created', 200)
|
||||
|
||||
abort(403)
|
||||
|
|
|
@ -3,11 +3,13 @@ import io
|
|||
import os.path
|
||||
import tarfile
|
||||
import base64
|
||||
import re
|
||||
|
||||
from github import Github, UnknownObjectException, GithubException
|
||||
from tempfile import SpooledTemporaryFile
|
||||
|
||||
from app import app, userfiles as user_files
|
||||
from util.tarfileappender import TarfileAppender
|
||||
|
||||
|
||||
client = app.config['HTTPCLIENT']
|
||||
|
@ -229,13 +231,35 @@ class GithubBuildTrigger(BuildTrigger):
|
|||
|
||||
return repos_by_org
|
||||
|
||||
def matches_branch(self, branch_name, regex):
|
||||
if not regex:
|
||||
return False
|
||||
|
||||
m = regex.match(branch_name)
|
||||
if not m:
|
||||
return False
|
||||
|
||||
return len(m.group(0)) == len(branch_name)
|
||||
|
||||
def list_build_subdirs(self, auth_token, config):
|
||||
gh_client = self._get_client(auth_token)
|
||||
source = config['build_source']
|
||||
|
||||
try:
|
||||
try:
|
||||
repo = gh_client.get_repo(source)
|
||||
default_commit = repo.get_branch(repo.default_branch or 'master').commit
|
||||
|
||||
# Find the first matching branch.
|
||||
branches = None
|
||||
if 'branch_regex' in config:
|
||||
try:
|
||||
regex = re.compile(config['branch_regex'])
|
||||
branches = [branch.name for branch in repo.get_branches()
|
||||
if self.matches_branch(branch.name, regex)]
|
||||
except:
|
||||
pass
|
||||
|
||||
branches = branches or [repo.default_branch or 'master']
|
||||
default_commit = repo.get_branch(branches[0]).commit
|
||||
commit_tree = repo.get_git_tree(default_commit.sha, recursive=True)
|
||||
|
||||
return [os.path.dirname(elem.path) for elem in commit_tree.tree
|
||||
|
@ -301,10 +325,17 @@ class GithubBuildTrigger(BuildTrigger):
|
|||
with tarfile.open(fileobj=tarball) as archive:
|
||||
tarball_subdir = archive.getnames()[0]
|
||||
|
||||
# Seek to position 0 to make boto multipart happy
|
||||
# Seek to position 0 to make tarfile happy.
|
||||
tarball.seek(0)
|
||||
|
||||
dockerfile_id = user_files.store_file(tarball, TARBALL_MIME)
|
||||
entries = {
|
||||
tarball_subdir + '/.git/HEAD': commit_sha,
|
||||
tarball_subdir + '/.git/objects/': None,
|
||||
tarball_subdir + '/.git/refs/': None
|
||||
}
|
||||
|
||||
appender = TarfileAppender(tarball, entries).get_stream()
|
||||
dockerfile_id = user_files.store_file(appender, TARBALL_MIME)
|
||||
|
||||
logger.debug('Successfully prepared job')
|
||||
|
||||
|
@ -330,7 +361,7 @@ class GithubBuildTrigger(BuildTrigger):
|
|||
payload = request.get_json()
|
||||
if not payload or payload.get('head_commit') is None:
|
||||
raise SkipRequestException()
|
||||
|
||||
|
||||
if 'zen' in payload:
|
||||
raise ValidationRequestException()
|
||||
|
||||
|
@ -339,6 +370,16 @@ class GithubBuildTrigger(BuildTrigger):
|
|||
commit_sha = payload['head_commit']['id']
|
||||
commit_message = payload['head_commit'].get('message', '')
|
||||
|
||||
if 'branch_regex' in config:
|
||||
try:
|
||||
regex = re.compile(config['branch_regex'])
|
||||
except:
|
||||
regex = re.compile('.*')
|
||||
|
||||
branch = ref.split('/')[-1]
|
||||
if not self.matches_branch(branch, regex):
|
||||
raise SkipRequestException()
|
||||
|
||||
if should_skip_commit(commit_message):
|
||||
raise SkipRequestException()
|
||||
|
||||
|
|
|
@ -4,11 +4,12 @@ import hashlib
|
|||
|
||||
from flask import redirect, Blueprint, abort, send_file
|
||||
|
||||
from app import storage as store, app
|
||||
from app import app
|
||||
from auth.auth import process_auth
|
||||
from auth.permissions import ReadRepositoryPermission
|
||||
from data import model
|
||||
from data import database
|
||||
from storage import Storage
|
||||
|
||||
from util.queuefile import QueueFile
|
||||
from util.queueprocess import QueueProcess
|
||||
|
@ -19,8 +20,9 @@ from util.dockerloadformat import build_docker_load_stream
|
|||
verbs = Blueprint('verbs', __name__)
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def _open_stream(namespace, repository, tag, synthetic_image_id, image_json, image_list):
|
||||
store = Storage(app)
|
||||
|
||||
def get_next_image():
|
||||
for current_image_id in image_list:
|
||||
yield model.get_repo_image(namespace, repository, current_image_id)
|
||||
|
@ -43,14 +45,23 @@ def _open_stream(namespace, repository, tag, synthetic_image_id, image_json, ima
|
|||
|
||||
|
||||
def _write_synthetic_image_to_storage(linked_storage_uuid, linked_locations, queue_file):
|
||||
database.configure(app.config)
|
||||
store = Storage(app)
|
||||
|
||||
def handle_exception(ex):
|
||||
logger.debug('Exception when building squashed image %s: %s', linked_storage_uuid, ex)
|
||||
model.delete_derived_storage_by_uuid(linked_storage_uuid)
|
||||
|
||||
queue_file.add_exception_handler(handle_exception)
|
||||
|
||||
image_path = store.image_layer_path(linked_storage_uuid)
|
||||
store.stream_write(linked_locations, image_path, queue_file)
|
||||
queue_file.close()
|
||||
|
||||
database.configure(app.config)
|
||||
done_uploading = model.get_storage_by_uuid(linked_storage_uuid)
|
||||
done_uploading.uploading = False
|
||||
done_uploading.save()
|
||||
if not queue_file.raised_exception:
|
||||
done_uploading = model.get_storage_by_uuid(linked_storage_uuid)
|
||||
done_uploading.uploading = False
|
||||
done_uploading.save()
|
||||
|
||||
|
||||
@verbs.route('/squash/<namespace>/<repository>/<tag>', methods=['GET'])
|
||||
|
@ -59,8 +70,9 @@ def get_squashed_tag(namespace, repository, tag):
|
|||
permission = ReadRepositoryPermission(namespace, repository)
|
||||
if permission.can() or model.repository_is_public(namespace, repository):
|
||||
# Lookup the requested tag.
|
||||
tag_image = model.get_tag_image(namespace, repository, tag)
|
||||
if not tag_image:
|
||||
try:
|
||||
tag_image = model.get_tag_image(namespace, repository, tag)
|
||||
except model.DataModelException:
|
||||
abort(404)
|
||||
|
||||
# Lookup the tag's image and storage.
|
||||
|
@ -68,6 +80,7 @@ def get_squashed_tag(namespace, repository, tag):
|
|||
if not repo_image:
|
||||
abort(404)
|
||||
|
||||
store = Storage(app)
|
||||
derived = model.find_or_create_derived_storage(repo_image.storage, 'squash',
|
||||
store.preferred_locations[0])
|
||||
if not derived.uploading:
|
||||
|
@ -96,8 +109,14 @@ def get_squashed_tag(namespace, repository, tag):
|
|||
|
||||
# Create a queue process to generate the data. The queue files will read from the process
|
||||
# and send the results to the client and storage.
|
||||
def _cleanup():
|
||||
# Close any existing DB connection once the process has exited.
|
||||
database.close_db_filter(None)
|
||||
|
||||
args = (namespace, repository, tag, synthetic_image_id, image_json, full_image_list)
|
||||
queue_process = QueueProcess(_open_stream, 8 * 1024, 10 * 1024 * 1024, args) # 8K/10M chunk/max
|
||||
queue_process = QueueProcess(_open_stream,
|
||||
8 * 1024, 10 * 1024 * 1024, # 8K/10M chunk/max
|
||||
args, finished=_cleanup)
|
||||
|
||||
client_queue_file = QueueFile(queue_process.create_queue(), 'client')
|
||||
storage_queue_file = QueueFile(queue_process.create_queue(), 'storage')
|
||||
|
@ -107,7 +126,7 @@ def get_squashed_tag(namespace, repository, tag):
|
|||
|
||||
# Start the storage saving.
|
||||
storage_args = (derived.uuid, derived.locations, storage_queue_file)
|
||||
QueueProcess.run_process(_write_synthetic_image_to_storage, storage_args)
|
||||
QueueProcess.run_process(_write_synthetic_image_to_storage, storage_args, finished=_cleanup)
|
||||
|
||||
# Return the client's data.
|
||||
return send_file(client_queue_file)
|
||||
|
|
2
events/build_failure.html
Normal file
2
events/build_failure.html
Normal file
|
@ -0,0 +1,2 @@
|
|||
<a href="{{ event_data.homepage }}">Build</a> failed for repository
|
||||
{{ event_data.repository | repository_reference }} ({{ event_data.build_id }}): {{ event_data.error_message }}
|
9
events/build_queued.html
Normal file
9
events/build_queued.html
Normal file
|
@ -0,0 +1,9 @@
|
|||
{% if event_data.is_manual and notification_data.performer_data.entity_name %}
|
||||
{{ notification_data.performer_data.entity_name | user_reference }} queued a
|
||||
<a href="{{ event_data.homepage }}">build</a>
|
||||
{% elif event_data.trigger_kind %}
|
||||
<a href="{{ event_data.homepage }}">Build</a> queued via a {{ event_data.trigger_kind }} trigger
|
||||
{% else %}
|
||||
<a href="{{ event_data.homepage }}">Build</a> queued
|
||||
{% endif %}
|
||||
for repository {{ event_data.repository | repository_reference }} ({{ event_data.build_id }})
|
2
events/build_start.html
Normal file
2
events/build_start.html
Normal file
|
@ -0,0 +1,2 @@
|
|||
<a href="{{ event_data.homepage }}">Build</a> started for repository
|
||||
{{ event_data.repository | repository_reference }} ({{ event_data.build_id }})
|
2
events/build_success.html
Normal file
2
events/build_success.html
Normal file
|
@ -0,0 +1,2 @@
|
|||
<a href="{{ event_data.homepage }}">Build</a> completed for repository
|
||||
{{ event_data.repository | repository_reference }} ({{ event_data.build_id }})
|
12
events/repo_push.html
Normal file
12
events/repo_push.html
Normal file
|
@ -0,0 +1,12 @@
|
|||
{% if notification_data.performer_data.entity_name %}
|
||||
{{ notification_data.performer_data.entity_name | user_reference }} pushed
|
||||
{% else %}
|
||||
Push of
|
||||
{% endif %}
|
||||
|
||||
{% if event_data.updated_tags %}
|
||||
{{ 'tags' | icon_image }}
|
||||
{% for tag in event_data.updated_tags %}{%if loop.index > 1 %}, {% endif %}{{ (event_data.repository, tag) | repository_tag_reference }}{% endfor %} in
|
||||
{% endif %}
|
||||
|
||||
repository {{ event_data.repository | repository_reference }}
|
22
initdb.py
22
initdb.py
|
@ -8,6 +8,7 @@ from datetime import datetime, timedelta
|
|||
from email.utils import formatdate
|
||||
from peewee import (SqliteDatabase, create_model_tables, drop_model_tables,
|
||||
savepoint_sqlite)
|
||||
from uuid import UUID
|
||||
|
||||
from data.database import *
|
||||
from data import model
|
||||
|
@ -20,18 +21,6 @@ logger = logging.getLogger(__name__)
|
|||
SAMPLE_DIFFS = ['test/data/sample/diffs/diffs%s.json' % i
|
||||
for i in range(1, 10)]
|
||||
|
||||
IMAGE_UUIDS = ['ab5160d1-8fb4-4022-a135-3c4de7f6ed97',
|
||||
'4259533e-868d-4db3-9a78-fc24ffc03a2b',
|
||||
'c2c6dc6e-24d1-4f15-a616-81c41e3e3629',
|
||||
'8ec59952-8f5a-4fa0-897e-57c3337e1914',
|
||||
'08a8ab1f-4aaa-4337-88ab-5b5c71a8d492',
|
||||
'4a71f3db-cbb1-4c3b-858f-1be032b3e875',
|
||||
'd40d531a-c70c-47f9-bf5b-2a4381db2d60',
|
||||
'6fe6cebb-52b2-4036-892e-b86d6487a56b',
|
||||
'e969ff76-e87d-4ea3-8cb3-0db9b5bcb8d9',
|
||||
'2e3b616b-301f-437c-98ab-37352f444a60',
|
||||
]
|
||||
|
||||
SAMPLE_CMDS = [["/bin/bash"],
|
||||
["/bin/sh", "-c",
|
||||
"echo \"PasswordAuthentication no\" >> /etc/ssh/sshd_config"],
|
||||
|
@ -57,6 +46,13 @@ def __gen_image_id(repo, image_num):
|
|||
return h.hexdigest() + h.hexdigest()
|
||||
|
||||
|
||||
def __gen_image_uuid(repo, image_num):
|
||||
str_to_hash = "%s/%s/%s" % (repo.namespace_user.username, repo.name, image_num)
|
||||
|
||||
h = hashlib.md5(str_to_hash)
|
||||
return UUID(bytes=h.digest())
|
||||
|
||||
|
||||
global_image_num = [0]
|
||||
def __create_subtree(repo, structure, creator_username, parent):
|
||||
num_nodes, subtrees, last_node_tags = structure
|
||||
|
@ -71,7 +67,7 @@ def __create_subtree(repo, structure, creator_username, parent):
|
|||
|
||||
new_image = model.find_create_or_link_image(docker_image_id, repo, None, {}, 'local_us')
|
||||
new_image_locations = new_image.storage.locations
|
||||
new_image.storage.uuid = IMAGE_UUIDS[image_num % len(IMAGE_UUIDS)]
|
||||
new_image.storage.uuid = __gen_image_uuid(repo, image_num)
|
||||
new_image.storage.uploading = False
|
||||
new_image.storage.checksum = checksum
|
||||
new_image.storage.save()
|
||||
|
|
13
registry.py
Normal file
13
registry.py
Normal file
|
@ -0,0 +1,13 @@
|
|||
import logging
|
||||
import logging.config
|
||||
|
||||
from app import app as application
|
||||
|
||||
from endpoints.index import index
|
||||
from endpoints.tags import tags
|
||||
from endpoints.registry import registry
|
||||
|
||||
|
||||
application.register_blueprint(index, url_prefix='/v1')
|
||||
application.register_blueprint(tags, url_prefix='/v1')
|
||||
application.register_blueprint(registry, url_prefix='/v1')
|
|
@ -18,7 +18,7 @@ paramiko
|
|||
xhtml2pdf
|
||||
redis
|
||||
hiredis
|
||||
docker-py
|
||||
git+https://github.com/devtable/docker-py.git@emptydirs
|
||||
pygithub
|
||||
flask-restful
|
||||
jsonschema
|
||||
|
|
|
@ -1,58 +1,57 @@
|
|||
APScheduler==3.0.0
|
||||
Flask==0.10.1
|
||||
Flask-Login==0.2.11
|
||||
Flask-Mail==0.9.0
|
||||
Flask-Mail==0.9.1
|
||||
Flask-Principal==0.4.0
|
||||
Flask-RESTful==0.2.12
|
||||
Jinja2==2.7.3
|
||||
LogentriesLogger==0.2.1
|
||||
Mako==1.0.0
|
||||
MarkupSafe==0.23
|
||||
Pillow==2.5.1
|
||||
PyGithub==1.25.0
|
||||
Pillow==2.6.0
|
||||
PyGithub==1.25.1
|
||||
PyMySQL==0.6.2
|
||||
PyPDF2==1.22
|
||||
PyPDF2==1.23
|
||||
PyYAML==3.11
|
||||
SQLAlchemy==0.9.7
|
||||
Werkzeug==0.9.6
|
||||
alembic==0.6.5
|
||||
git+https://github.com/DevTable/aniso8601-fake.git
|
||||
git+https://github.com/DevTable/anunidecode.git
|
||||
argparse==1.2.1
|
||||
alembic==0.6.7
|
||||
backports.ssl-match-hostname==3.4.0.2
|
||||
beautifulsoup4==4.3.2
|
||||
blinker==1.3
|
||||
boto==2.32.0
|
||||
coverage==3.7.1
|
||||
docker-py==0.4.0
|
||||
boto==2.32.1
|
||||
git+https://github.com/devtable/docker-py.git@emptydirs
|
||||
ecdsa==0.11
|
||||
futures==2.1.6
|
||||
futures==2.2.0
|
||||
gevent==1.0.1
|
||||
greenlet==0.4.2
|
||||
gipc==0.4.0
|
||||
greenlet==0.4.4
|
||||
gunicorn==18.0
|
||||
hiredis==0.1.4
|
||||
hiredis==0.1.5
|
||||
html5lib==0.999
|
||||
itsdangerous==0.24
|
||||
jsonschema==2.3.0
|
||||
jsonschema==2.4.0
|
||||
marisa-trie==0.6
|
||||
mixpanel-py==3.1.3
|
||||
mock==1.0.1
|
||||
git+https://github.com/NateFerrero/oauth2lib.git
|
||||
paramiko==1.14.0
|
||||
peewee==2.2.5
|
||||
mixpanel-py==3.2.0
|
||||
paramiko==1.15.1
|
||||
peewee==2.3.3
|
||||
psycopg2==2.5.4
|
||||
py-bcrypt==0.4
|
||||
pycrypto==2.6.1
|
||||
python-dateutil==2.2
|
||||
python-ldap==2.4.15
|
||||
python-ldap==2.4.17
|
||||
python-magic==0.4.6
|
||||
pytz==2014.4
|
||||
psycopg2==2.5.3
|
||||
pytz==2014.7
|
||||
raven==5.0.0
|
||||
redis==2.10.1
|
||||
redis==2.10.3
|
||||
reportlab==2.7
|
||||
requests==2.3.0
|
||||
six==1.7.3
|
||||
requests==2.4.3
|
||||
six==1.8.0
|
||||
stripe==1.19.0
|
||||
tzlocal==1.1.1
|
||||
websocket-client==0.11.0
|
||||
websocket-client==0.18.0
|
||||
wsgiref==0.1.2
|
||||
xhtml2pdf==0.0.6
|
||||
|
|
|
@ -3974,7 +3974,7 @@ pre.command:before {
|
|||
color: #00b0ed;
|
||||
}
|
||||
|
||||
.contact-options .option-phone .fa-circle {
|
||||
.contact-options .option-tel .fa-circle {
|
||||
color: #1dd924;
|
||||
}
|
||||
|
||||
|
@ -3982,10 +3982,14 @@ pre.command:before {
|
|||
color: #e52f00;
|
||||
}
|
||||
|
||||
.contact-options .option-email .fa-circle {
|
||||
.contact-options .option-mailto .fa-circle {
|
||||
color: #1b72f1;
|
||||
}
|
||||
|
||||
.contact-options .option-url .fa-circle {
|
||||
color: #F1A51B;
|
||||
}
|
||||
|
||||
.about-us .row {
|
||||
margin-bottom: 30px;
|
||||
}
|
||||
|
@ -4105,6 +4109,27 @@ pre.command:before {
|
|||
border-bottom-left-radius: 0px;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .branch-reference.not-match {
|
||||
color: #ccc !important;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .branch-reference.not-match a {
|
||||
color: #ccc !important;
|
||||
text-decoration: line-through;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .branch-filter {
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .branch-filter span {
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .selected-info {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .github-org-icon {
|
||||
width: 20px;
|
||||
margin-right: 8px;
|
||||
|
@ -4120,6 +4145,45 @@ pre.command:before {
|
|||
padding-left: 6px;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .matching-branches {
|
||||
margin: 0px;
|
||||
padding: 0px;
|
||||
margin-left: 10px;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .matching-branches li:before {
|
||||
content: "\f126";
|
||||
font-family: FontAwesome;
|
||||
}
|
||||
|
||||
.trigger-setup-github-element .matching-branches li {
|
||||
list-style: none;
|
||||
display: inline-block;
|
||||
margin-left: 10px;
|
||||
}
|
||||
|
||||
.setup-trigger-directive-element .dockerfile-found-content {
|
||||
margin-left: 32px;
|
||||
}
|
||||
|
||||
.setup-trigger-directive-element .dockerfile-found-content:before {
|
||||
content: "\f071";
|
||||
font-family: FontAwesome;
|
||||
color: rgb(255, 194, 0);
|
||||
position: absolute;
|
||||
top: 0px;
|
||||
left: 0px;
|
||||
font-size: 20px;
|
||||
}
|
||||
|
||||
.setup-trigger-directive-element .dockerfile-found {
|
||||
position: relative;
|
||||
margin-bottom: 16px;
|
||||
padding-bottom: 16px;
|
||||
border-bottom: 1px solid #eee;
|
||||
}
|
||||
|
||||
.slideinout {
|
||||
-webkit-transition:0.5s all;
|
||||
transition:0.5s linear all;
|
||||
|
@ -4127,7 +4191,7 @@ pre.command:before {
|
|||
|
||||
position: relative;
|
||||
|
||||
height: 75px;
|
||||
height: 32px;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
|
|
|
@ -8,102 +8,110 @@
|
|||
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">×</button>
|
||||
<h4 class="modal-title">Setup new build trigger</h4>
|
||||
</div>
|
||||
<div class="modal-body" ng-show="activating">
|
||||
<div class="modal-body" ng-show="currentView == 'activating'">
|
||||
<span class="quay-spinner"></span> Setting up trigger...
|
||||
</div>
|
||||
<div class="modal-body" ng-show="!activating">
|
||||
<div class="modal-body" ng-show="currentView != 'activating'">
|
||||
<!-- Trigger-specific setup -->
|
||||
<div class="trigger-description-element trigger-option-section" ng-switch on="trigger.service">
|
||||
<div ng-switch-when="github">
|
||||
<div class="trigger-setup-github" repository="repository" trigger="trigger"
|
||||
next-step-counter="nextStepCounter" current-step-valid="state.stepValid"
|
||||
analyze="checkAnalyze(isValid)"></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Loading pull information -->
|
||||
<div ng-show="currentView == 'analyzing'">
|
||||
<span class="quay-spinner"></span> Checking pull credential requirements...
|
||||
</div>
|
||||
|
||||
<!-- Pull information -->
|
||||
<div class="trigger-option-section" ng-show="showPullRequirements">
|
||||
<div ng-show="!pullRequirements">
|
||||
<span class="quay-spinner"></span> Checking pull credential requirements...
|
||||
</div>
|
||||
<div class="trigger-option-section" ng-show="currentView == 'analyzed'">
|
||||
|
||||
<div ng-show="pullRequirements">
|
||||
<div class="alert alert-danger" ng-if="pullRequirements.status == 'error'">
|
||||
{{ pullRequirements.message }}
|
||||
</div>
|
||||
<div class="alert alert-warning" ng-if="pullRequirements.status == 'warning'">
|
||||
{{ pullRequirements.message }}
|
||||
</div>
|
||||
<div class="alert alert-success" ng-if="pullRequirements.status == 'analyzed' && pullRequirements.is_public === false">
|
||||
The
|
||||
<a href="{{ pullRequirements.dockerfile_url }}" ng-if="pullRequirements.dockerfile_url" target="_blank">Dockerfile found</a>
|
||||
<span ng-if="!pullRequirements.dockerfile_url">Dockerfile found</span>
|
||||
depends on the private <span class="registry-name"></span> repository
|
||||
<a href="/repository/{{ pullRequirements.namespace }}/{{ pullRequirements.name }}" target="_blank">
|
||||
{{ pullRequirements.namespace }}/{{ pullRequirements.name }}
|
||||
</a> which requires
|
||||
a robot account for pull access, because it is marked <strong>private</strong>.
|
||||
<!-- Messaging -->
|
||||
<div class="alert alert-danger" ng-if="pullInfo.analysis.status == 'error'">
|
||||
{{ pullInfo.analysis.message }}
|
||||
</div>
|
||||
<div class="alert alert-warning" ng-if="pullInfo.analysis.status == 'warning'">
|
||||
{{ pullRequirements.message }}
|
||||
</div>
|
||||
<div class="dockerfile-found" ng-if="pullInfo.analysis.is_public === false">
|
||||
<div class="dockerfile-found-content">
|
||||
A robot account is <strong>required</strong> for this build trigger because
|
||||
|
||||
the
|
||||
<a href="{{ pullInfo.analysis.dockerfile_url }}" ng-if="pullInfo.analysis.dockerfile_url" target="_blank">
|
||||
Dockerfile found
|
||||
</a>
|
||||
<span ng-if="!pullInfo.analysis.dockerfile_url">Dockerfile found</span>
|
||||
|
||||
pulls from the private <span class="registry-name"></span> repository
|
||||
|
||||
<a href="/repository/{{ pullInfo.analysis.namespace }}/{{ pullInfo.analysis.name }}" target="_blank">
|
||||
{{ pullInfo.analysis.namespace }}/{{ pullInfo.analysis.name }}
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div ng-show="pullRequirements">
|
||||
<table style="width: 100%;">
|
||||
<tr>
|
||||
<td style="width: 162px">
|
||||
<span class="context-tooltip" data-title="The credentials given to 'docker pull' in the builder for pulling images"
|
||||
style="margin-bottom: 10px" bs-tooltip>
|
||||
docker pull Credentials:
|
||||
</span>
|
||||
</td>
|
||||
<td>
|
||||
<div ng-if="!isNamespaceAdmin(repository.namespace)" style="color: #aaa;">
|
||||
In order to set pull credentials for a build trigger, you must be an Administrator of the namespace <strong>{{ repository.namespace }}</strong>
|
||||
</div>
|
||||
<div class="btn-group btn-group-sm" ng-if="isNamespaceAdmin(repository.namespace)">
|
||||
<button type="button" class="btn btn-default"
|
||||
ng-class="publicPull ? 'active btn-info' : ''" ng-click="setPublicPull(true)">None</button>
|
||||
<button type="button" class="btn btn-default"
|
||||
ng-class="publicPull ? '' : 'active btn-info'" ng-click="setPublicPull(false)">
|
||||
<i class="fa fa-wrench"></i>
|
||||
Robot account
|
||||
</button>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
<div style="margin-bottom: 12px">Please select the credentials to use when pulling the base image:</div>
|
||||
<div ng-if="!isNamespaceAdmin(repository.namespace)" style="color: #aaa;">
|
||||
<strong>Note:</strong> In order to set pull credentials for a build trigger, you must be an
|
||||
Administrator of the namespace <strong>{{ repository.namespace }}</strong>
|
||||
</div>
|
||||
|
||||
<table style="width: 100%;">
|
||||
<tr ng-show="!publicPull">
|
||||
<td>
|
||||
<div class="entity-search" namespace="repository.namespace"
|
||||
placeholder="'Select robot account for pulling...'"
|
||||
current-entity="pullEntity"
|
||||
allowed-entities="['robot']"></div>
|
||||
<!-- Namespace admin -->
|
||||
<div ng-show="isNamespaceAdmin(repository.namespace)">
|
||||
<!-- Select credentials -->
|
||||
<div class="btn-group btn-group-sm">
|
||||
<button type="button" class="btn btn-default"
|
||||
ng-class="pullInfo.is_public ? 'active btn-info' : ''"
|
||||
ng-click="pullInfo.is_public = true">
|
||||
None
|
||||
</button>
|
||||
<button type="button" class="btn btn-default"
|
||||
ng-class="pullInfo.is_public ? '' : 'active btn-info'"
|
||||
ng-click="pullInfo.is_public = false">
|
||||
<i class="fa fa-wrench"></i>
|
||||
Robot account
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<div class="alert alert-info" ng-if="pullRequirements.status == 'analyzed' && pullRequirements.robots.length"
|
||||
style="margin-top: 20px; margin-bottom: 0px;">
|
||||
Note: We've automatically selected robot account
|
||||
<span class="entity-reference" entity="pullRequirements.robots[0]"></span>, since it has access to the private
|
||||
repository.
|
||||
</div>
|
||||
<div class="alert alert-warning"
|
||||
ng-if="pullRequirements.status == 'analyzed' && !pullRequirements.robots.length && pullRequirements.name"
|
||||
style="margin-top: 20px; margin-bottom: 0px;">
|
||||
Note: No robot account currently has access to the private repository. Please create one and/or assign access in the
|
||||
<a href="/repository/{{ pullRequirements.namespace }}/{{ pullRequirements.name }}/admin" target="_blank">repository's
|
||||
admin panel</a>.
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
<!-- Robot Select -->
|
||||
<div ng-show="!pullInfo.is_public" style="margin-top: 10px">
|
||||
<div class="entity-search" namespace="repository.namespace"
|
||||
placeholder="'Select robot account for pulling...'"
|
||||
current-entity="pullInfo.pull_entity"
|
||||
allowed-entities="['robot']"></div>
|
||||
|
||||
<div ng-if="pullInfo.analysis.robots.length" style="margin-top: 20px; margin-bottom: 0px;">
|
||||
<strong>Note</strong>: We've automatically selected robot account
|
||||
<span class="entity-reference" entity="pullInfo.analysis.robots[0]"></span>,
|
||||
since it has access to the private repository.
|
||||
</div>
|
||||
<div ng-if="!pullInfo.analysis.robots.length && pullInfo.analysis.name"
|
||||
style="margin-top: 20px; margin-bottom: 0px;">
|
||||
<strong>Note</strong>: No robot account currently has access to the private repository. Please create one and/or assign access in the
|
||||
<a href="/repository/{{ pullInfo.analysis.namespace }}/{{ pullInfo.analysis.name }}/admin" target="_blank">
|
||||
repository's admin panel.
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button type="button" class="btn btn-primary" ng-disabled="!state.stepValid"
|
||||
ng-click="nextStepCounter = nextStepCounter + 1"
|
||||
ng-show="currentView == 'config'">Next</button>
|
||||
|
||||
<button type="button" class="btn btn-primary"
|
||||
ng-disabled="!trigger.$ready || (!publicPull && !pullEntity) || checkingPullRequirements || activating"
|
||||
ng-click="activate()">Finished</button>
|
||||
ng-disabled="!trigger.$ready || (!pullInfo['is_public'] && !pullInfo['pull_entity'])"
|
||||
ng-click="activate()"
|
||||
ng-show="currentView == 'analyzed'">Create Trigger</button>
|
||||
|
||||
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button>
|
||||
</div>
|
||||
</div><!-- /.modal-content -->
|
||||
|
|
9
static/directives/step-view-step.html
Normal file
9
static/directives/step-view-step.html
Normal file
|
@ -0,0 +1,9 @@
|
|||
<span class="step-view-step-content">
|
||||
<span ng-show="!loading">
|
||||
<span ng-transclude></span>
|
||||
</span>
|
||||
<span ng-show="loading">
|
||||
<span class="quay-spinner"></span>
|
||||
{{ loadMessage }}
|
||||
</span>
|
||||
</span>
|
3
static/directives/step-view.html
Normal file
3
static/directives/step-view.html
Normal file
|
@ -0,0 +1,3 @@
|
|||
<div class="step-view-element">
|
||||
<div class="transcluded" ng-transclude>
|
||||
</div>
|
|
@ -2,19 +2,18 @@
|
|||
<span ng-switch-when="github">
|
||||
<i class="fa fa-github fa-lg" style="margin-right: 6px" data-title="GitHub" bs-tooltip="tooltip.title"></i>
|
||||
Push to GitHub repository <a href="https://github.com/{{ trigger.config.build_source }}" target="_new">{{ trigger.config.build_source }}</a>
|
||||
<div style="margin-top: 4px; margin-left: 26px; font-size: 12px; color: gray;" ng-if="trigger.config.subdir">
|
||||
<span>Dockerfile:
|
||||
<a href="https://github.com/{{ trigger.config.build_source }}/tree/{{ trigger.config.master_branch || 'master' }}/{{ trigger.config.subdir }}/Dockerfile" target="_blank">
|
||||
//{{ trigger.config.subdir }}/Dockerfile
|
||||
</a>
|
||||
</span>
|
||||
</div>
|
||||
<div style="margin-top: 4px; margin-left: 26px; font-size: 12px; color: gray;" ng-if="!trigger.config.subdir && !short">
|
||||
<span><span class="trigger-description-subtitle">Dockerfile:</span>
|
||||
<a href="https://github.com/{{ trigger.config.build_source }}/tree/{{ trigger.config.master_branch || 'master' }}/Dockerfile" target="_blank">
|
||||
//Dockerfile
|
||||
</a>
|
||||
</span>
|
||||
<div style="margin-top: 4px; margin-left: 26px; font-size: 12px; color: gray;" ng-if="!short">
|
||||
<div>
|
||||
<span class="trigger-description-subtitle">Branches:</span>
|
||||
<span ng-if="trigger.config.branch_regex">Matching Regular Expression {{ trigger.config.branch_regex }}</span>
|
||||
<span ng-if="!trigger.config.branch_regex">(All Branches)</span>
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<span class="trigger-description-subtitle">Dockerfile:</span>
|
||||
<span ng-if="trigger.config.subdir">//{{ trigger.config.subdir}}/Dockerfile</span>
|
||||
<span ng-if="!trigger.config.subdir">//Dockerfile</span>
|
||||
</div>
|
||||
</div>
|
||||
</span>
|
||||
<span ng-switch-default>
|
||||
|
|
|
@ -1,48 +1,147 @@
|
|||
<div class="trigger-setup-github-element">
|
||||
<div ng-show="loading">
|
||||
<span class="quay-spinner" style="vertical-align: middle; margin-right: 10px"></span>
|
||||
Loading Repository List
|
||||
<!-- Current selected info -->
|
||||
<div class="selected-info" ng-show="nextStepCounter > 0">
|
||||
<table style="width: 100%;">
|
||||
<tr ng-show="currentRepo && nextStepCounter > 0">
|
||||
<td width="200px">
|
||||
Repository:
|
||||
</td>
|
||||
<td>
|
||||
<div class="current-repo">
|
||||
<img class="dropdown-select-icon github-org-icon"
|
||||
ng-src="{{ currentRepo.avatar_url ? currentRepo.avatar_url : '//www.gravatar.com/avatar/' }}">
|
||||
{{ currentRepo.repo }}
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr ng-show="nextStepCounter > 1">
|
||||
<td>
|
||||
Branches:
|
||||
</td>
|
||||
<td>
|
||||
<div class="branch-filter">
|
||||
<span ng-if="!state.hasBranchFilter">(All Branches)</span>
|
||||
<span ng-if="state.hasBranchFilter">Regular Expression: <code>{{ state.branchFilter }}</code></span>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr ng-show="nextStepCounter > 2">
|
||||
<td>
|
||||
Dockerfile Location:
|
||||
</td>
|
||||
<td>
|
||||
<div class="dockerfile-location">
|
||||
<i class="fa fa-folder fa-lg"></i> {{ state.currentLocation || '(Repository Root)' }}
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
<div ng-show="!loading">
|
||||
<div style="margin-bottom: 18px">Please choose the GitHub repository that will trigger the build:</div>
|
||||
|
||||
|
||||
<!-- Step view -->
|
||||
<div class="step-view" next-step-counter="nextStepCounter" current-step-valid="currentStepValid"
|
||||
steps-completed="stepsCompleted()">
|
||||
<!-- Repository select -->
|
||||
<div class="dropdown-select" placeholder="'Select a repository'" selected-item="currentRepo"
|
||||
lookahead-items="repoLookahead">
|
||||
<!-- Icons -->
|
||||
<i class="dropdown-select-icon none-icon fa fa-github fa-lg"></i>
|
||||
<img class="dropdown-select-icon github-org-icon" ng-src="{{ currentRepo.avatar_url ? currentRepo.avatar_url : '//www.gravatar.com/avatar/' }}">
|
||||
<div class="step-view-step" complete-condition="currentRepo" load-callback="loadRepositories(callback)"
|
||||
load-message="Loading Repositories">
|
||||
<div style="margin-bottom: 12px">Please choose the GitHub repository that will trigger the build:</div>
|
||||
<div class="dropdown-select" placeholder="'Select a repository'" selected-item="currentRepo"
|
||||
lookahead-items="repoLookahead">
|
||||
<!-- Icons -->
|
||||
<i class="dropdown-select-icon none-icon fa fa-github fa-lg"></i>
|
||||
<img class="dropdown-select-icon github-org-icon"
|
||||
ng-src="{{ currentRepo.avatar_url ? currentRepo.avatar_url : '//www.gravatar.com/avatar/' }}">
|
||||
|
||||
<!-- Dropdown menu -->
|
||||
<ul class="dropdown-select-menu" role="menu">
|
||||
<li ng-repeat-start="org in orgs" role="presentation" class="dropdown-header github-org-header">
|
||||
<img ng-src="{{ org.info.avatar_url }}" class="github-org-icon">{{ org.info.name }}
|
||||
</li>
|
||||
<li ng-repeat="repo in org.repos" class="github-repo-listing">
|
||||
<a href="javascript:void(0)" ng-click="selectRepo(repo, org)"><i class="fa fa-github fa-lg"></i> {{ repo }}</a>
|
||||
</li>
|
||||
<li role="presentation" class="divider" ng-repeat-end ng-show="$index < orgs.length - 1"></li>
|
||||
</ul>
|
||||
<!-- Dropdown menu -->
|
||||
<ul class="dropdown-select-menu" role="menu">
|
||||
<li ng-repeat-start="org in orgs" role="presentation" class="dropdown-header github-org-header">
|
||||
<img ng-src="{{ org.info.avatar_url }}" class="github-org-icon">{{ org.info.name }}
|
||||
</li>
|
||||
<li ng-repeat="repo in org.repos" class="github-repo-listing">
|
||||
<a href="javascript:void(0)" ng-click="selectRepo(repo, org)"><i class="fa fa-github fa-lg"></i> {{ repo }}</a>
|
||||
</li>
|
||||
<li role="presentation" class="divider" ng-repeat-end ng-show="$index < orgs.length - 1"></li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Branch filter/select -->
|
||||
<div class="step-view-step" complete-condition="!state.hasBranchFilter || state.branchFilter"
|
||||
load-callback="loadBranches(callback)"
|
||||
load-message="Loading Branches">
|
||||
|
||||
<div style="margin-bottom: 12px">Please choose the branches to which this trigger will apply:</div>
|
||||
<div style="margin-left: 20px;">
|
||||
<div class="btn-group btn-group-sm" style="margin-bottom: 12px">
|
||||
<button type="button" class="btn btn-default"
|
||||
ng-class="state.hasBranchFilter ? '' : 'active btn-info'" ng-click="state.hasBranchFilter = false">
|
||||
All Branches
|
||||
</button>
|
||||
<button type="button" class="btn btn-default"
|
||||
ng-class="state.hasBranchFilter ? 'active btn-info' : ''" ng-click="state.hasBranchFilter = true">
|
||||
Matching Regular Expression
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<div ng-show="state.hasBranchFilter" style="margin-top: 10px;">
|
||||
<form>
|
||||
<input class="form-control" type="text" ng-model="state.branchFilter"
|
||||
placeholder="(Regular expression)" required>
|
||||
</form>
|
||||
|
||||
<div style="margin-top: 10px">
|
||||
<div ng-if="branchNames.length">
|
||||
Branches:
|
||||
<ul class="matching-branches">
|
||||
<li ng-repeat="branchName in branchNames | limitTo:20"
|
||||
class="branch-reference"
|
||||
ng-class="isMatchingBranch(branchName, state.branchFilter) ? 'match' : 'not-match'">
|
||||
<a href="https://github.com/{{ currentRepo.repo }}/tree/{{ branchName }}" target="_blank">
|
||||
{{ branchName }}
|
||||
</a>
|
||||
</li>
|
||||
</ul>
|
||||
<span ng-if="branchNames.length > 20">...</span>
|
||||
</div>
|
||||
<div ng-if="state.branchFilter && !branchNames.length"
|
||||
style="margin-top: 10px">
|
||||
<strong>Warning:</strong> No branches found
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Dockerfile folder select -->
|
||||
<div class="slideinout" ng-show="currentRepo">
|
||||
<div style="margin-top: 10px">Dockerfile Location:</div>
|
||||
<div class="dropdown-select" placeholder="'(Repository Root)'" selected-item="currentLocation"
|
||||
lookahead-items="locations" handle-input="handleLocationInput(input)" handle-item-selected="handleLocationSelected(datum)"
|
||||
<div class="step-view-step" complete-condition="trigger.$ready" load-callback="loadLocations(callback)"
|
||||
load-message="Loading Folders">
|
||||
|
||||
<div style="margin-bottom: 12px">Dockerfile Location:</div>
|
||||
<div class="dropdown-select" placeholder="'(Repository Root)'" selected-item="state.currentLocation"
|
||||
lookahead-items="locations" handle-input="handleLocationInput(input)"
|
||||
handle-item-selected="handleLocationSelected(datum)"
|
||||
allow-custom-input="true">
|
||||
<!-- Icons -->
|
||||
<i class="dropdown-select-icon none-icon fa fa-folder-o fa-lg" ng-show="isInvalidLocation"></i>
|
||||
<i class="dropdown-select-icon none-icon fa fa-folder fa-lg" style="color: black;" ng-show="!isInvalidLocation"></i>
|
||||
<i class="dropdown-select-icon none-icon fa fa-folder-o fa-lg" ng-show="state.isInvalidLocation"></i>
|
||||
<i class="dropdown-select-icon none-icon fa fa-folder fa-lg" style="color: black;" ng-show="!state.isInvalidLocation"></i>
|
||||
<i class="dropdown-select-icon fa fa-folder fa-lg"></i>
|
||||
|
||||
<!-- Dropdown menu -->
|
||||
<ul class="dropdown-select-menu" role="menu">
|
||||
<li ng-repeat="location in locations">
|
||||
<a href="javascript:void(0)" ng-click="setLocation(location)" ng-if="!location"><i class="fa fa-github fa-lg"></i> Repository Root</a>
|
||||
<a href="javascript:void(0)" ng-click="setLocation(location)" ng-if="location"><i class="fa fa-folder fa-lg"></i> {{ location }}</a>
|
||||
<a href="javascript:void(0)" ng-click="setLocation(location)" ng-if="!location">
|
||||
<i class="fa fa-github fa-lg"></i> Repository Root
|
||||
</a>
|
||||
<a href="javascript:void(0)" ng-click="setLocation(location)" ng-if="location">
|
||||
<i class="fa fa-folder fa-lg"></i> {{ location }}
|
||||
</a>
|
||||
</li>
|
||||
<li class="dropdown-header" role="presentation" ng-show="!locations.length">No Dockerfiles found in repository</li>
|
||||
<li class="dropdown-header" role="presentation" ng-show="!locations.length">
|
||||
No Dockerfiles found in repository
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
|
@ -53,10 +152,10 @@
|
|||
<div class="alert alert-warning" ng-show="locationError">
|
||||
{{ locationError }}
|
||||
</div>
|
||||
<div class="alert alert-info" ng-show="locations.length && isInvalidLocation">
|
||||
<div class="alert alert-info" ng-show="locations.length && state.isInvalidLocation">
|
||||
Note: The folder does not currently exist or contain a Dockerfile
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- /step-view -->
|
||||
</div>
|
||||
</div>
|
||||
|
|
BIN
static/img/icons/tags.png
Normal file
BIN
static/img/icons/tags.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 294 B |
BIN
static/img/icons/wrench.png
Normal file
BIN
static/img/icons/wrench.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 379 B |
372
static/js/app.js
372
static/js/app.js
|
@ -2989,6 +2989,28 @@ quayApp.directive('dockerAuthDialog', function (Config) {
|
|||
});
|
||||
|
||||
|
||||
quayApp.filter('regex', function() {
|
||||
return function(input, regex) {
|
||||
if (!regex) { return []; }
|
||||
|
||||
try {
|
||||
var patt = new RegExp(regex);
|
||||
} catch (ex) {
|
||||
return [];
|
||||
}
|
||||
|
||||
var out = [];
|
||||
for (var i = 0; i < input.length; ++i){
|
||||
var m = input[i].match(patt);
|
||||
if (m && m[0].length == input[i].length) {
|
||||
out.push(input[i]);
|
||||
}
|
||||
}
|
||||
return out;
|
||||
};
|
||||
});
|
||||
|
||||
|
||||
quayApp.filter('reverse', function() {
|
||||
return function(items) {
|
||||
return items.slice().reverse();
|
||||
|
@ -4745,6 +4767,118 @@ quayApp.directive('triggerDescription', function () {
|
|||
});
|
||||
|
||||
|
||||
quayApp.directive('stepView', function ($compile) {
|
||||
var directiveDefinitionObject = {
|
||||
priority: 0,
|
||||
templateUrl: '/static/directives/step-view.html',
|
||||
replace: true,
|
||||
transclude: true,
|
||||
restrict: 'C',
|
||||
scope: {
|
||||
'nextStepCounter': '=nextStepCounter',
|
||||
'currentStepValid': '=currentStepValid',
|
||||
|
||||
'stepsCompleted': '&stepsCompleted'
|
||||
},
|
||||
controller: function($scope, $element, $rootScope) {
|
||||
this.currentStepIndex = -1;
|
||||
this.steps = [];
|
||||
this.watcher = null;
|
||||
|
||||
this.getCurrentStep = function() {
|
||||
return this.steps[this.currentStepIndex];
|
||||
};
|
||||
|
||||
this.reset = function() {
|
||||
this.currentStepIndex = -1;
|
||||
for (var i = 0; i < this.steps.length; ++i) {
|
||||
this.steps[i].element.hide();
|
||||
}
|
||||
|
||||
$scope.currentStepValid = false;
|
||||
};
|
||||
|
||||
this.next = function() {
|
||||
if (this.currentStepIndex >= 0) {
|
||||
if (!this.getCurrentStep().scope.completeCondition) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.getCurrentStep().element.hide();
|
||||
|
||||
if (this.unwatch) {
|
||||
this.unwatch();
|
||||
this.unwatch = null;
|
||||
}
|
||||
}
|
||||
|
||||
this.currentStepIndex++;
|
||||
|
||||
if (this.currentStepIndex < this.steps.length) {
|
||||
var currentStep = this.getCurrentStep();
|
||||
currentStep.element.show();
|
||||
currentStep.scope.load()
|
||||
|
||||
this.unwatch = currentStep.scope.$watch('completeCondition', function(cc) {
|
||||
$scope.currentStepValid = !!cc;
|
||||
});
|
||||
} else {
|
||||
$scope.stepsCompleted();
|
||||
}
|
||||
};
|
||||
|
||||
this.register = function(scope, element) {
|
||||
element.hide();
|
||||
|
||||
this.steps.push({
|
||||
'scope': scope,
|
||||
'element': element
|
||||
});
|
||||
};
|
||||
|
||||
var that = this;
|
||||
$scope.$watch('nextStepCounter', function(nsc) {
|
||||
if (nsc >= 0) {
|
||||
that.next();
|
||||
} else {
|
||||
that.reset();
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
return directiveDefinitionObject;
|
||||
});
|
||||
|
||||
|
||||
quayApp.directive('stepViewStep', function () {
|
||||
var directiveDefinitionObject = {
|
||||
priority: 1,
|
||||
require: '^stepView',
|
||||
templateUrl: '/static/directives/step-view-step.html',
|
||||
replace: false,
|
||||
transclude: true,
|
||||
restrict: 'C',
|
||||
scope: {
|
||||
'completeCondition': '=completeCondition',
|
||||
'loadCallback': '&loadCallback',
|
||||
'loadMessage': '@loadMessage'
|
||||
},
|
||||
link: function(scope, element, attrs, controller) {
|
||||
controller.register(scope, element);
|
||||
},
|
||||
controller: function($scope, $element) {
|
||||
$scope.load = function() {
|
||||
$scope.loading = true;
|
||||
$scope.loadCallback({'callback': function() {
|
||||
$scope.loading = false;
|
||||
}});
|
||||
};
|
||||
}
|
||||
};
|
||||
return directiveDefinitionObject;
|
||||
});
|
||||
|
||||
|
||||
quayApp.directive('dropdownSelect', function ($compile) {
|
||||
var directiveDefinitionObject = {
|
||||
priority: 0,
|
||||
|
@ -4987,25 +5121,28 @@ quayApp.directive('setupTriggerDialog', function () {
|
|||
controller: function($scope, $element, ApiService, UserService) {
|
||||
var modalSetup = false;
|
||||
|
||||
$scope.state = {};
|
||||
$scope.nextStepCounter = -1;
|
||||
$scope.currentView = 'config';
|
||||
|
||||
$scope.show = function() {
|
||||
if (!$scope.trigger || !$scope.repository) { return; }
|
||||
|
||||
$scope.activating = false;
|
||||
$scope.pullEntity = null;
|
||||
$scope.publicPull = true;
|
||||
$scope.showPullRequirements = false;
|
||||
|
||||
$scope.currentView = 'config';
|
||||
$('#setupTriggerModal').modal({});
|
||||
|
||||
if (!modalSetup) {
|
||||
$('#setupTriggerModal').on('hidden.bs.modal', function () {
|
||||
if (!$scope.trigger || $scope.trigger['is_active']) { return; }
|
||||
|
||||
$scope.nextStepCounter = -1;
|
||||
$scope.$apply(function() {
|
||||
$scope.cancelSetupTrigger();
|
||||
});
|
||||
});
|
||||
|
||||
modalSetup = true;
|
||||
$scope.nextStepCounter = 0;
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -5018,27 +5155,20 @@ quayApp.directive('setupTriggerDialog', function () {
|
|||
};
|
||||
|
||||
$scope.hide = function() {
|
||||
$scope.activating = false;
|
||||
$('#setupTriggerModal').modal('hide');
|
||||
};
|
||||
|
||||
$scope.setPublicPull = function(value) {
|
||||
$scope.publicPull = value;
|
||||
};
|
||||
|
||||
$scope.checkAnalyze = function(isValid) {
|
||||
$scope.currentView = 'analyzing';
|
||||
$scope.pullInfo = {
|
||||
'is_public': true
|
||||
};
|
||||
|
||||
if (!isValid) {
|
||||
$scope.publicPull = true;
|
||||
$scope.pullEntity = null;
|
||||
$scope.showPullRequirements = false;
|
||||
$scope.checkingPullRequirements = false;
|
||||
$scope.currentView = 'analyzed';
|
||||
return;
|
||||
}
|
||||
|
||||
$scope.checkingPullRequirements = true;
|
||||
$scope.showPullRequirements = true;
|
||||
$scope.pullRequirements = null;
|
||||
|
||||
var params = {
|
||||
'repository': $scope.repository.namespace + '/' + $scope.repository.name,
|
||||
'trigger_uuid': $scope.trigger.id
|
||||
|
@ -5049,26 +5179,20 @@ quayApp.directive('setupTriggerDialog', function () {
|
|||
};
|
||||
|
||||
ApiService.analyzeBuildTrigger(data, params).then(function(resp) {
|
||||
$scope.pullRequirements = resp;
|
||||
|
||||
if (resp['status'] == 'publicbase') {
|
||||
$scope.publicPull = true;
|
||||
$scope.pullEntity = null;
|
||||
} else if (resp['namespace']) {
|
||||
$scope.publicPull = false;
|
||||
$scope.currentView = 'analyzed';
|
||||
|
||||
if (resp['status'] == 'analyzed') {
|
||||
if (resp['robots'] && resp['robots'].length > 0) {
|
||||
$scope.pullEntity = resp['robots'][0];
|
||||
} else {
|
||||
$scope.pullEntity = null;
|
||||
$scope.pullInfo['pull_entity'] = resp['robots'][0];
|
||||
} else {
|
||||
$scope.pullInfo['pull_entity'] = null;
|
||||
}
|
||||
|
||||
$scope.pullInfo['is_public'] = false;
|
||||
}
|
||||
|
||||
$scope.checkingPullRequirements = false;
|
||||
}, function(resp) {
|
||||
$scope.pullRequirements = resp;
|
||||
$scope.checkingPullRequirements = false;
|
||||
});
|
||||
$scope.pullInfo['analysis'] = resp;
|
||||
}, ApiService.errorDisplay('Cannot load Dockerfile information'));
|
||||
};
|
||||
|
||||
$scope.activate = function() {
|
||||
|
@ -5081,11 +5205,11 @@ quayApp.directive('setupTriggerDialog', function () {
|
|||
'config': $scope.trigger['config']
|
||||
};
|
||||
|
||||
if ($scope.pullEntity) {
|
||||
data['pull_robot'] = $scope.pullEntity['name'];
|
||||
if ($scope.pullInfo['pull_entity']) {
|
||||
data['pull_robot'] = $scope.pullInfo['pull_entity']['name'];
|
||||
}
|
||||
|
||||
$scope.activating = true;
|
||||
$scope.currentView = 'activating';
|
||||
|
||||
var errorHandler = ApiService.errorDisplay('Cannot activate build trigger', function(resp) {
|
||||
$scope.hide();
|
||||
|
@ -5126,17 +5250,99 @@ quayApp.directive('triggerSetupGithub', function () {
|
|||
scope: {
|
||||
'repository': '=repository',
|
||||
'trigger': '=trigger',
|
||||
|
||||
'nextStepCounter': '=nextStepCounter',
|
||||
'currentStepValid': '=currentStepValid',
|
||||
|
||||
'analyze': '&analyze'
|
||||
},
|
||||
controller: function($scope, $element, ApiService) {
|
||||
$scope.analyzeCounter = 0;
|
||||
$scope.setupReady = false;
|
||||
$scope.loading = true;
|
||||
|
||||
$scope.branchNames = null;
|
||||
|
||||
$scope.state = {
|
||||
'branchFilter': '',
|
||||
'hasBranchFilter': false,
|
||||
'isInvalidLocation': true,
|
||||
'currentLocation': null
|
||||
};
|
||||
|
||||
$scope.isMatchingBranch = function(branchName, filter) {
|
||||
try {
|
||||
var patt = new RegExp(filter);
|
||||
} catch (ex) {
|
||||
return false;
|
||||
}
|
||||
|
||||
var m = branchName.match(patt);
|
||||
return m && m[0].length == branchName.length;
|
||||
}
|
||||
|
||||
$scope.stepsCompleted = function() {
|
||||
$scope.analyze({'isValid': !$scope.state.isInvalidLocation});
|
||||
};
|
||||
|
||||
$scope.loadRepositories = function(callback) {
|
||||
var params = {
|
||||
'repository': $scope.repository.namespace + '/' + $scope.repository.name,
|
||||
'trigger_uuid': $scope.trigger.id
|
||||
};
|
||||
|
||||
ApiService.listTriggerBuildSources(null, params).then(function(resp) {
|
||||
$scope.orgs = resp['sources'];
|
||||
setupTypeahead();
|
||||
callback();
|
||||
}, ApiService.errorDisplay('Cannot load repositories'));
|
||||
};
|
||||
|
||||
$scope.loadBranches = function(callback) {
|
||||
var params = {
|
||||
'repository': $scope.repository.namespace + '/' + $scope.repository.name,
|
||||
'trigger_uuid': $scope.trigger['id'],
|
||||
'field_name': 'branch_name'
|
||||
};
|
||||
|
||||
ApiService.listTriggerFieldValues($scope.trigger['config'], params).then(function(resp) {
|
||||
$scope.branchNames = resp['values'];
|
||||
callback();
|
||||
}, ApiService.errorDisplay('Cannot load branch names'));
|
||||
};
|
||||
|
||||
$scope.loadLocations = function(callback) {
|
||||
$scope.locations = null;
|
||||
|
||||
var params = {
|
||||
'repository': $scope.repository.namespace + '/' + $scope.repository.name,
|
||||
'trigger_uuid': $scope.trigger.id
|
||||
};
|
||||
|
||||
ApiService.listBuildTriggerSubdirs($scope.trigger['config'], params).then(function(resp) {
|
||||
if (resp['status'] == 'error') {
|
||||
callback(resp['message'] || 'Could not load Dockerfile locations');
|
||||
return;
|
||||
}
|
||||
|
||||
$scope.locations = resp['subdir'] || [];
|
||||
|
||||
// Select a default location (if any).
|
||||
if ($scope.locations.length > 0) {
|
||||
$scope.setLocation($scope.locations[0]);
|
||||
} else {
|
||||
$scope.state.currentLocation = null;
|
||||
$scope.state.isInvalidLocation = resp['subdir'].indexOf('') < 0;
|
||||
$scope.trigger.$ready = true;
|
||||
}
|
||||
|
||||
callback();
|
||||
}, ApiService.errorDisplay('Cannot load locations'));
|
||||
}
|
||||
|
||||
$scope.handleLocationInput = function(location) {
|
||||
$scope.state.isInvalidLocation = $scope.locations.indexOf(location) < 0;
|
||||
$scope.trigger['config']['subdir'] = location || '';
|
||||
$scope.isInvalidLocation = $scope.locations.indexOf(location) < 0;
|
||||
$scope.analyze({'isValid': !$scope.isInvalidLocation});
|
||||
$scope.trigger.$ready = true;
|
||||
};
|
||||
|
||||
$scope.handleLocationSelected = function(datum) {
|
||||
|
@ -5144,10 +5350,10 @@ quayApp.directive('triggerSetupGithub', function () {
|
|||
};
|
||||
|
||||
$scope.setLocation = function(location) {
|
||||
$scope.currentLocation = location;
|
||||
$scope.state.currentLocation = location;
|
||||
$scope.state.isInvalidLocation = false;
|
||||
$scope.trigger['config']['subdir'] = location || '';
|
||||
$scope.isInvalidLocation = false;
|
||||
$scope.analyze({'isValid': true});
|
||||
$scope.trigger.$ready = true;
|
||||
};
|
||||
|
||||
$scope.selectRepo = function(repo, org) {
|
||||
|
@ -5161,10 +5367,7 @@ quayApp.directive('triggerSetupGithub', function () {
|
|||
};
|
||||
|
||||
$scope.selectRepoInternal = function(currentRepo) {
|
||||
if (!currentRepo) {
|
||||
$scope.trigger.$ready = false;
|
||||
return;
|
||||
}
|
||||
$scope.trigger.$ready = false;
|
||||
|
||||
var params = {
|
||||
'repository': $scope.repository.namespace + '/' + $scope.repository.name,
|
||||
|
@ -5176,39 +5379,6 @@ quayApp.directive('triggerSetupGithub', function () {
|
|||
'build_source': repo,
|
||||
'subdir': ''
|
||||
};
|
||||
|
||||
// Lookup the possible Dockerfile locations.
|
||||
$scope.locations = null;
|
||||
if (repo) {
|
||||
ApiService.listBuildTriggerSubdirs($scope.trigger['config'], params).then(function(resp) {
|
||||
if (resp['status'] == 'error') {
|
||||
$scope.locationError = resp['message'] || 'Could not load Dockerfile locations';
|
||||
$scope.locations = null;
|
||||
$scope.trigger.$ready = false;
|
||||
$scope.isInvalidLocation = false;
|
||||
$scope.analyze({'isValid': false});
|
||||
return;
|
||||
}
|
||||
|
||||
$scope.locationError = null;
|
||||
$scope.locations = resp['subdir'] || [];
|
||||
$scope.trigger.$ready = true;
|
||||
|
||||
if ($scope.locations.length > 0) {
|
||||
$scope.setLocation($scope.locations[0]);
|
||||
} else {
|
||||
$scope.currentLocation = null;
|
||||
$scope.isInvalidLocation = resp['subdir'].indexOf('') < 0;
|
||||
$scope.analyze({'isValid': !$scope.isInvalidLocation});
|
||||
}
|
||||
}, function(resp) {
|
||||
$scope.locationError = resp['message'] || 'Could not load Dockerfile locations';
|
||||
$scope.locations = null;
|
||||
$scope.trigger.$ready = false;
|
||||
$scope.isInvalidLocation = false;
|
||||
$scope.analyze({'isValid': false});
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
var setupTypeahead = function() {
|
||||
|
@ -5238,30 +5408,20 @@ quayApp.directive('triggerSetupGithub', function () {
|
|||
$scope.repoLookahead = repos;
|
||||
};
|
||||
|
||||
var loadSources = function() {
|
||||
var params = {
|
||||
'repository': $scope.repository.namespace + '/' + $scope.repository.name,
|
||||
'trigger_uuid': $scope.trigger.id
|
||||
};
|
||||
|
||||
ApiService.listTriggerBuildSources(null, params).then(function(resp) {
|
||||
$scope.orgs = resp['sources'];
|
||||
setupTypeahead();
|
||||
$scope.loading = false;
|
||||
});
|
||||
};
|
||||
|
||||
var check = function() {
|
||||
if ($scope.repository && $scope.trigger) {
|
||||
loadSources();
|
||||
}
|
||||
};
|
||||
|
||||
$scope.$watch('repository', check);
|
||||
$scope.$watch('trigger', check);
|
||||
|
||||
$scope.$watch('currentRepo', function(repo) {
|
||||
$scope.selectRepoInternal(repo);
|
||||
if (repo) {
|
||||
$scope.selectRepoInternal(repo);
|
||||
}
|
||||
});
|
||||
|
||||
$scope.$watch('state.branchFilter', function(bf) {
|
||||
if (!$scope.trigger) { return; }
|
||||
|
||||
if ($scope.state.hasBranchFilter) {
|
||||
$scope.trigger['config']['branch_regex'] = bf;
|
||||
} else {
|
||||
delete $scope.trigger['config']['branch_regex'];
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
@ -6315,6 +6475,14 @@ quayApp.directive('ngVisible', function () {
|
|||
};
|
||||
});
|
||||
|
||||
quayApp.config( [
|
||||
'$compileProvider',
|
||||
function( $compileProvider )
|
||||
{
|
||||
$compileProvider.aHrefSanitizationWhitelist(/^\s*(https?|ftp|mailto|tel|irc):/);
|
||||
}
|
||||
]);
|
||||
|
||||
quayApp.run(['$location', '$rootScope', 'Restangular', 'UserService', 'PlanService', '$http', '$timeout', 'CookieService', 'Features', '$anchorScroll',
|
||||
function($location, $rootScope, Restangular, UserService, PlanService, $http, $timeout, CookieService, Features, $anchorScroll) {
|
||||
|
||||
|
|
|
@ -8,7 +8,49 @@ function GuideCtrl() {
|
|||
function SecurityCtrl($scope) {
|
||||
}
|
||||
|
||||
function ContactCtrl($scope) {
|
||||
function ContactCtrl($scope, Config) {
|
||||
$scope.Config = Config;
|
||||
$scope.colsize = Math.floor(12 / Config.CONTACT_INFO.length);
|
||||
|
||||
$scope.getKind = function(contactInfo) {
|
||||
var colon = contactInfo.indexOf(':');
|
||||
var scheme = contactInfo.substr(0, colon);
|
||||
if (scheme == 'https' || scheme == 'http') {
|
||||
if (contactInfo.indexOf('//twitter.com/') > 0) {
|
||||
return 'twitter';
|
||||
}
|
||||
|
||||
return 'url';
|
||||
}
|
||||
|
||||
return scheme;
|
||||
};
|
||||
|
||||
$scope.getTitle = function(contactInfo) {
|
||||
switch ($scope.getKind(contactInfo)) {
|
||||
case 'url':
|
||||
return contactInfo;
|
||||
|
||||
case 'twitter':
|
||||
var parts = contactInfo.split('/');
|
||||
return '@' + parts[parts.length - 1];
|
||||
|
||||
case 'tel':
|
||||
return contactInfo.substr('tel:'.length);
|
||||
|
||||
case 'irc':
|
||||
// irc://chat.freenode.net:6665/quayio
|
||||
var parts = contactInfo.substr('irc://'.length).split('/');
|
||||
var server = parts[0];
|
||||
if (server.indexOf('freenode') > 0) {
|
||||
server = 'Freenode';
|
||||
}
|
||||
return server + ': #' + parts[parts.length - 1];
|
||||
|
||||
case 'mailto':
|
||||
return contactInfo.substr('mailto:'.length);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function PlansCtrl($scope, $location, UserService, PlanService, $routeParams) {
|
||||
|
@ -426,7 +468,7 @@ function RepoCtrl($scope, $sanitize, Restangular, ImageMetadataService, ApiServi
|
|||
});
|
||||
|
||||
if ($scope.currentTag) {
|
||||
var squash = 'curl -f ' + Config.getHost('ACCOUNTNAME:PASSWORDORTOKEN');
|
||||
var squash = 'curl -L -f ' + Config.getHost('ACCOUNTNAME:PASSWORDORTOKEN');
|
||||
squash += '/c1/squash/' + namespace + '/' + name + '/' + $scope.currentTag.name;
|
||||
squash += ' | docker load';
|
||||
|
||||
|
|
|
@ -901,7 +901,7 @@ ImageHistoryTree.prototype.toggle_ = function(d) {
|
|||
ImageHistoryTree.prototype.dispose = function() {
|
||||
var container = this.container_ ;
|
||||
$('#' + container).removeOverscroll();
|
||||
document.getElementById(container).innerHTML = '';
|
||||
$('#' + container).html('');
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
|
|
@ -5,40 +5,21 @@
|
|||
</h2>
|
||||
|
||||
<div class="row contact-options">
|
||||
<div class="col-sm-3 text-center option-email">
|
||||
<div class="text-center" ng-repeat="info in Config.CONTACT_INFO"
|
||||
ng-class="['option-' + getKind(info), 'col-sm-' + colsize]">
|
||||
<span class="fa-stack fa-3x text-center">
|
||||
<i class="fa fa-circle fa-stack-2x"></i>
|
||||
<i class="fa fa-envelope fa-stack-1x fa-inverse"></i>
|
||||
<i class="fa fa-stack-1x fa-inverse"
|
||||
ng-class="{'mailto': 'fa-envelope', 'irc': 'fa-comment', 'tel': 'fa-phone', 'twitter': 'fa-twitter', 'url': 'fa-ticket'}[getKind(info)]"></i>
|
||||
</span>
|
||||
<h4>Email Us</h4>
|
||||
<h4><a href="mailto:support@quay.io">support@quay.io</a></h4>
|
||||
</div>
|
||||
|
||||
<div class="col-sm-3 text-center option-irc">
|
||||
<span class="fa-stack fa-3x">
|
||||
<i class="fa fa-circle fa-stack-2x"></i>
|
||||
<i class="fa fa-comment fa-stack-1x fa-inverse"></i>
|
||||
<span ng-switch="getKind(info)">
|
||||
<h4 ng-switch-when="mailto">Email</h4>
|
||||
<h4 ng-switch-when="irc">IRC</h4>
|
||||
<h4 ng-switch-when="tel">Call</h4>
|
||||
<h4 ng-switch-when="twitter">Tweet</h4>
|
||||
<h4 ng-switch-when="url">Help System</h4>
|
||||
</span>
|
||||
<h4>IRC</h4>
|
||||
<h4><a href="irc://chat.freenode.net:6665/quayio">Freenode: #quayio</a></h4>
|
||||
</div>
|
||||
|
||||
<div class="col-sm-3 text-center option-phone">
|
||||
<span class="fa-stack fa-3x">
|
||||
<i class="fa fa-circle fa-stack-2x"></i>
|
||||
<i class="fa fa-phone fa-stack-1x fa-inverse"></i>
|
||||
</span>
|
||||
<h4>Call Us</h4>
|
||||
<h4><a href="tel:+1-888-930-3475">888-930-3475</a></h4>
|
||||
</div>
|
||||
|
||||
<div class="col-sm-3 text-center option-twitter">
|
||||
<span class="fa-stack fa-3x">
|
||||
<i class="fa fa-circle fa-stack-2x"></i>
|
||||
<i class="fa fa-twitter fa-stack-1x fa-inverse"></i>
|
||||
</span>
|
||||
<h4>Tweet Us</h4>
|
||||
<h4><a href="https://twitter.com/quayio">@quayio</a></h4>
|
||||
<h4><a ng-href="{{ info }}">{{ getTitle(info) }}</a></h4>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
|
@ -116,7 +116,7 @@ mixpanel.init("{{ mixpanel_key }}", { track_pageview : false, debug: {{ is_debug
|
|||
<li quay-require="['BILLING']"><a href="/privacy" target="_self">Privacy</a></li>
|
||||
<li quay-require="['BILLING']"><a href="/security/" target="_self">Security</a></li>
|
||||
<li quay-require="['BILLING']"><a href="/about/" target="_self">About</a></li>
|
||||
<li><b><a href="/contact/" target="_self">Contact</a></b></li>
|
||||
<li><b><a href="{{ contact_href or '/contact/' }}" target="_self">Contact</a></b></li>
|
||||
<li quay-require="['BILLING']"><b><a href="http://status.quay.io" target="_self">Service Status</a></b></li>
|
||||
</ul>
|
||||
</div>
|
||||
|
|
|
@ -0,0 +1,85 @@
|
|||
{
|
||||
"removed": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"added": [
|
||||
"/opt/elasticsearch/LICENSE.txt",
|
||||
"/opt/elasticsearch/NOTICE.txt",
|
||||
"/opt/elasticsearch/README.textile",
|
||||
"/opt/elasticsearch/bin/elasticsearch",
|
||||
"/opt/elasticsearch/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch/bin/plugin",
|
||||
"/opt/elasticsearch/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch/config/logging.yml",
|
||||
"/opt/elasticsearch/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,38 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release.gpg",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_source_Sources",
|
||||
"/var/lib/apt/lists/lock",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release.gpg",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_source_Sources"
|
||||
],
|
||||
"changed": [
|
||||
"/var/cache/apt/pkgcache.bin",
|
||||
"/var/cache/apt/srcpkgcache.bin"
|
||||
]
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [],
|
||||
"changed": []
|
||||
}
|
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,85 @@
|
|||
{
|
||||
"removed": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"added": [
|
||||
"/opt/elasticsearch/LICENSE.txt",
|
||||
"/opt/elasticsearch/NOTICE.txt",
|
||||
"/opt/elasticsearch/README.textile",
|
||||
"/opt/elasticsearch/bin/elasticsearch",
|
||||
"/opt/elasticsearch/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch/bin/plugin",
|
||||
"/opt/elasticsearch/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch/config/logging.yml",
|
||||
"/opt/elasticsearch/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/root/.bash_history",
|
||||
"/usr/sbin/policy-rc.d"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,38 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release.gpg",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_source_Sources",
|
||||
"/var/lib/apt/lists/lock",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release.gpg",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_source_Sources"
|
||||
],
|
||||
"changed": [
|
||||
"/var/cache/apt/pkgcache.bin",
|
||||
"/var/cache/apt/srcpkgcache.bin"
|
||||
]
|
||||
}
|
|
@ -0,0 +1,85 @@
|
|||
{
|
||||
"removed": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"added": [
|
||||
"/opt/elasticsearch/LICENSE.txt",
|
||||
"/opt/elasticsearch/NOTICE.txt",
|
||||
"/opt/elasticsearch/README.textile",
|
||||
"/opt/elasticsearch/bin/elasticsearch",
|
||||
"/opt/elasticsearch/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch/bin/plugin",
|
||||
"/opt/elasticsearch/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch/config/logging.yml",
|
||||
"/opt/elasticsearch/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,38 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release.gpg",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_source_Sources",
|
||||
"/var/lib/apt/lists/lock",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release.gpg",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_source_Sources"
|
||||
],
|
||||
"changed": [
|
||||
"/var/cache/apt/pkgcache.bin",
|
||||
"/var/cache/apt/srcpkgcache.bin"
|
||||
]
|
||||
}
|
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,38 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_Release.gpg",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_main_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/archive.ubuntu.com_ubuntu_dists_raring_universe_source_Sources",
|
||||
"/var/lib/apt/lists/lock",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_Release.gpg",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_main_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_multiverse_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_restricted_source_Sources",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_binary-amd64_Packages",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_i18n_Translation-en",
|
||||
"/var/lib/apt/lists/security.ubuntu.com_ubuntu_dists_raring-security_universe_source_Sources"
|
||||
],
|
||||
"changed": [
|
||||
"/var/cache/apt/pkgcache.bin",
|
||||
"/var/cache/apt/srcpkgcache.bin"
|
||||
]
|
||||
}
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/elasticsearch-0.90.5.tar.gz"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,85 @@
|
|||
{
|
||||
"removed": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"added": [
|
||||
"/opt/elasticsearch/LICENSE.txt",
|
||||
"/opt/elasticsearch/NOTICE.txt",
|
||||
"/opt/elasticsearch/README.textile",
|
||||
"/opt/elasticsearch/bin/elasticsearch",
|
||||
"/opt/elasticsearch/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch/bin/plugin",
|
||||
"/opt/elasticsearch/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch/config/logging.yml",
|
||||
"/opt/elasticsearch/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/root/.bash_history",
|
||||
"/usr/sbin/policy-rc.d"
|
||||
],
|
||||
"changed": []
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,45 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,85 @@
|
|||
{
|
||||
"removed": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"added": [
|
||||
"/opt/elasticsearch/LICENSE.txt",
|
||||
"/opt/elasticsearch/NOTICE.txt",
|
||||
"/opt/elasticsearch/README.textile",
|
||||
"/opt/elasticsearch/bin/elasticsearch",
|
||||
"/opt/elasticsearch/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch/bin/plugin",
|
||||
"/opt/elasticsearch/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch/config/logging.yml",
|
||||
"/opt/elasticsearch/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,85 @@
|
|||
{
|
||||
"removed": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"added": [
|
||||
"/opt/elasticsearch/LICENSE.txt",
|
||||
"/opt/elasticsearch/NOTICE.txt",
|
||||
"/opt/elasticsearch/README.textile",
|
||||
"/opt/elasticsearch/bin/elasticsearch",
|
||||
"/opt/elasticsearch/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch/bin/plugin",
|
||||
"/opt/elasticsearch/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch/config/logging.yml",
|
||||
"/opt/elasticsearch/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/root/.bash_history",
|
||||
"/usr/sbin/policy-rc.d"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/opt/elasticsearch-0.90.5/LICENSE.txt",
|
||||
"/opt/elasticsearch-0.90.5/NOTICE.txt",
|
||||
"/opt/elasticsearch-0.90.5/README.textile",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch",
|
||||
"/opt/elasticsearch-0.90.5/bin/elasticsearch.in.sh",
|
||||
"/opt/elasticsearch-0.90.5/bin/plugin",
|
||||
"/opt/elasticsearch-0.90.5/config/elasticsearch.yml",
|
||||
"/opt/elasticsearch-0.90.5/config/logging.yml",
|
||||
"/opt/elasticsearch-0.90.5/lib/elasticsearch-0.90.5.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jna-3.3.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/jts-1.12.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/log4j-1.2.17.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-analyzers-common-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-codecs-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-core-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-grouping-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-highlighter-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-join-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-memory-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-misc-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queries-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-queryparser-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-sandbox-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-spatial-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/lucene-suggest-4.4.0.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-amd64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-ia64-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-sparc64-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-universal64-macosx.dylib",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-5.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-freebsd-6.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-linux.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/libsigar-x86-solaris.so",
|
||||
"/opt/elasticsearch-0.90.5/lib/sigar/sigar-1.6.4.jar",
|
||||
"/opt/elasticsearch-0.90.5/lib/spatial4j-0.3.jar"
|
||||
],
|
||||
"changed": []
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/elasticsearch-0.90.5.tar.gz"
|
||||
],
|
||||
"changed": []
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"removed": [],
|
||||
"added": [
|
||||
"/elasticsearch-0.90.5.tar.gz"
|
||||
],
|
||||
"changed": []
|
||||
}
|
File diff suppressed because it is too large
Load diff
Some files were not shown because too many files have changed in this diff Show more
Reference in a new issue