From b6678513858c5c4ad55082cec137e6870a22f7a4 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Sat, 13 Jul 2013 10:46:58 -0500 Subject: Fix completion percentage calculation in mirror status We sometimes record a duration even on a failed fetch attempt, such as if we get an HTTP 404. However, we never record a last_sync value on a failed fetch. Use this field instead to sum up the total number of successful checks. Signed-off-by: Dan McGee --- mirrors/utils.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/mirrors/utils.py b/mirrors/utils.py index bba8e36b..633731a7 100644 --- a/mirrors/utils.py +++ b/mirrors/utils.py @@ -35,7 +35,7 @@ def status_data(cutoff_time, mirror_id=None): sql = """ SELECT l.url_id, u.mirror_id, COUNT(l.id) AS check_count, - COUNT(l.duration) AS success_count, + COUNT(l.last_sync) AS success_count, MAX(l.last_sync) AS last_sync, MAX(l.check_time) AS last_check, AVG(l.duration) AS duration_avg, @@ -51,7 +51,7 @@ def status_data(cutoff_time, mirror_id=None): sql = """ SELECT l.url_id, u.mirror_id, COUNT(l.id) AS check_count, - COUNT(l.duration) AS success_count, + COUNT(l.last_sync) AS success_count, MAX(l.last_sync) AS last_sync, MAX(l.check_time) AS last_check, AVG(l.duration) AS duration_avg, -- cgit v1.2.3-54-g00ecf From 1b5b1caaf87d13b14a4f02f7e5026644352f1209 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Mon, 12 Aug 2013 09:53:03 -0500 Subject: Bump South requirements.txt version Signed-off-by: Dan McGee --- requirements.txt | 2 +- requirements_prod.txt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/requirements.txt b/requirements.txt index 1909da1b..79bd1616 100644 --- a/requirements.txt +++ b/requirements.txt @@ -2,7 +2,7 @@ Django==1.5.1 IPy==0.81 Markdown==2.3.1 -South==0.8.1 +South==0.8.2 bencode==1.0 django-countries==1.5 jsmin==2.0.3 diff --git a/requirements_prod.txt b/requirements_prod.txt index 425a6576..a8b380df 100644 --- a/requirements_prod.txt +++ b/requirements_prod.txt @@ -2,7 +2,7 @@ Django==1.5.1 IPy==0.81 Markdown==2.3.1 -South==0.8.1 +South==0.8.2 bencode==1.0 django-countries==1.5 jsmin==2.0.3 -- cgit v1.2.3-54-g00ecf From 8b3aa69158db4284c8d8005ce3a0f517bdac3078 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Mon, 30 Sep 2013 20:00:13 -0500 Subject: Bump to latest Django security release Signed-off-by: Dan McGee --- requirements.txt | 2 +- requirements_prod.txt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/requirements.txt b/requirements.txt index 79bd1616..ac873e63 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,5 +1,5 @@ -e git+git://github.com/fredj/cssmin.git@master#egg=cssmin -Django==1.5.1 +Django==1.5.4 IPy==0.81 Markdown==2.3.1 South==0.8.2 diff --git a/requirements_prod.txt b/requirements_prod.txt index a8b380df..79299c86 100644 --- a/requirements_prod.txt +++ b/requirements_prod.txt @@ -1,5 +1,5 @@ -e git+git://github.com/fredj/cssmin.git@master#egg=cssmin -Django==1.5.1 +Django==1.5.4 IPy==0.81 Markdown==2.3.1 South==0.8.2 -- cgit v1.2.3-54-g00ecf From b3321537d3ec91fd6f8d1123881a94a0490f1bdc Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Mon, 30 Sep 2013 20:01:14 -0500 Subject: Bump jsmin requirements version Signed-off-by: Dan McGee --- requirements.txt | 2 +- requirements_prod.txt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/requirements.txt b/requirements.txt index ac873e63..53aaa05c 100644 --- a/requirements.txt +++ b/requirements.txt @@ -5,6 +5,6 @@ Markdown==2.3.1 South==0.8.2 bencode==1.0 django-countries==1.5 -jsmin==2.0.3 +jsmin==2.0.4 pgpdump==1.4 pytz>=2013b diff --git a/requirements_prod.txt b/requirements_prod.txt index 79299c86..7cc19970 100644 --- a/requirements_prod.txt +++ b/requirements_prod.txt @@ -5,7 +5,7 @@ Markdown==2.3.1 South==0.8.2 bencode==1.0 django-countries==1.5 -jsmin==2.0.3 +jsmin==2.0.4 pgpdump==1.4 psycopg2==2.5.1 pyinotify==0.9.4 -- cgit v1.2.3-54-g00ecf From 92136757bfd20563999b0e1cf3f05685b60da6bd Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Mon, 30 Sep 2013 20:39:59 -0500 Subject: Proper support for revoked signatures The 'valid' column wasn't quite right. Add a new 'revoked' column that works similar to the one we have on keys and use it instead, properly parsing the output from `gpg` signature data and looking for the magic prefix string. Signed-off-by: Dan McGee --- devel/admin.py | 3 +- devel/management/commands/pgp_import.py | 38 ++++--- ...nature_valid__add_field_pgpsignature_revoked.py | 125 +++++++++++++++++++++ devel/models.py | 2 +- public/views.py | 8 +- 5 files changed, 155 insertions(+), 21 deletions(-) create mode 100644 devel/migrations/0011_auto__del_field_pgpsignature_valid__add_field_pgpsignature_revoked.py diff --git a/devel/admin.py b/devel/admin.py index 971933b7..c8f80f95 100644 --- a/devel/admin.py +++ b/devel/admin.py @@ -29,8 +29,7 @@ class DeveloperKeyAdmin(admin.ModelAdmin): class PGPSignatureAdmin(admin.ModelAdmin): - list_display = ('signer', 'signee', 'created', 'expires', 'valid') - list_filter = ('valid',) + list_display = ('signer', 'signee', 'created', 'expires', 'revoked') search_fields = ('signer', 'signee') date_hierarchy = 'created' diff --git a/devel/management/commands/pgp_import.py b/devel/management/commands/pgp_import.py index b1f29d77..faa9ff5e 100644 --- a/devel/management/commands/pgp_import.py +++ b/devel/management/commands/pgp_import.py @@ -176,8 +176,13 @@ def import_keys(keyring): logger.info("created %d, updated %d keys", created_ct, updated_ct) -SignatureData = namedtuple('SignatureData', - ('signer', 'signee', 'created', 'expires', 'valid')) +class SignatureData(object): + def __init__(self, signer, signee, created): + self.signer = signer + self.signee = signee + self.created = created + self.expires = None + self.revoked = None def parse_sigdata(data): @@ -192,21 +197,26 @@ def parse_sigdata(data): if parts[0] == 'pub': current_pubkey = parts[4] nodes[current_pubkey] = None - if parts[0] == 'uid': + elif parts[0] == 'uid': uid = parts[9] # only set uid if this is the first one encountered if nodes[current_pubkey] is None: nodes[current_pubkey] = uid - if parts[0] == 'sig': + elif parts[0] == 'sig': signer = parts[4] created = get_date(parts[5]) - expires = None + edge = SignatureData(signer, current_pubkey, created) if parts[6]: - expires = get_date(parts[6]) - valid = parts[1] != '-' - edge = SignatureData(signer, current_pubkey, - created, expires, valid) + edge.expires = get_date(parts[6]) edges.append(edge) + elif parts[0] == 'rev': + signer = parts[4] + revoked = get_date(parts[5]) + # revoke any prior edges that match + matches = [e for e in edges if e.signer == signer + and e.signee == current_pubkey] + for edge in matches: + edge.revoked = revoked return nodes, edges @@ -220,18 +230,18 @@ def import_signatures(keyring): pruned_edges = {edge for edge in edges if edge.signer in nodes and edge.signer != edge.signee} - logger.info("creating or finding %d signatures", len(pruned_edges)) + logger.info("creating or finding up to %d signatures", len(pruned_edges)) created_ct = updated_ct = 0 with transaction.commit_on_success(): for edge in pruned_edges: sig, created = PGPSignature.objects.get_or_create( signer=edge.signer, signee=edge.signee, created=edge.created, expires=edge.expires, - defaults={ 'valid': edge.valid }) - if sig.valid != edge.valid: - sig.valid = edge.valid + defaults={ 'revoked': edge.revoked }) + if sig.revoked != edge.revoked: + sig.revoked = edge.revoked sig.save() - updated_ct = 1 + updated_ct += 1 if created: created_ct += 1 diff --git a/devel/migrations/0011_auto__del_field_pgpsignature_valid__add_field_pgpsignature_revoked.py b/devel/migrations/0011_auto__del_field_pgpsignature_valid__add_field_pgpsignature_revoked.py new file mode 100644 index 00000000..a2df917f --- /dev/null +++ b/devel/migrations/0011_auto__del_field_pgpsignature_valid__add_field_pgpsignature_revoked.py @@ -0,0 +1,125 @@ +# -*- coding: utf-8 -*- +import datetime +from south.db import db +from south.v2 import SchemaMigration +from django.db import models + + +class Migration(SchemaMigration): + + def forwards(self, orm): + db.delete_column(u'devel_pgpsignature', 'valid') + db.add_column(u'devel_pgpsignature', 'revoked', + self.gf('django.db.models.fields.DateField')(null=True, blank=True), + keep_default=False) + + + def backwards(self, orm): + db.add_column(u'devel_pgpsignature', 'valid', + self.gf('django.db.models.fields.BooleanField')(default=True), + keep_default=True) + db.delete_column(u'devel_pgpsignature', 'revoked') + + + models = { + u'auth.group': { + 'Meta': {'object_name': 'Group'}, + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '80'}), + 'permissions': ('django.db.models.fields.related.ManyToManyField', [], {'to': u"orm['auth.Permission']", 'symmetrical': 'False', 'blank': 'True'}) + }, + u'auth.permission': { + 'Meta': {'ordering': "(u'content_type__app_label', u'content_type__model', u'codename')", 'unique_together': "((u'content_type', u'codename'),)", 'object_name': 'Permission'}, + 'codename': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'content_type': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['contenttypes.ContentType']"}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '50'}) + }, + u'auth.user': { + 'Meta': {'object_name': 'User'}, + 'date_joined': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'email': ('django.db.models.fields.EmailField', [], {'max_length': '75', 'blank': 'True'}), + 'first_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'groups': ('django.db.models.fields.related.ManyToManyField', [], {'to': u"orm['auth.Group']", 'symmetrical': 'False', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'is_active': ('django.db.models.fields.BooleanField', [], {'default': 'True'}), + 'is_staff': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'is_superuser': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'last_login': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'last_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'password': ('django.db.models.fields.CharField', [], {'max_length': '128'}), + 'user_permissions': ('django.db.models.fields.related.ManyToManyField', [], {'to': u"orm['auth.Permission']", 'symmetrical': 'False', 'blank': 'True'}), + 'username': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '30'}) + }, + u'contenttypes.contenttype': { + 'Meta': {'ordering': "('name',)", 'unique_together': "(('app_label', 'model'),)", 'object_name': 'ContentType', 'db_table': "'django_content_type'"}, + 'app_label': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'model': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '100'}) + }, + u'devel.developerkey': { + 'Meta': {'object_name': 'DeveloperKey'}, + 'created': ('django.db.models.fields.DateTimeField', [], {}), + 'expires': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'key': ('devel.fields.PGPKeyField', [], {'unique': 'True', 'max_length': '40'}), + 'owner': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'all_keys'", 'null': 'True', 'to': u"orm['auth.User']"}), + 'parent': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['devel.DeveloperKey']", 'null': 'True', 'on_delete': 'models.SET_NULL'}), + 'revoked': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}) + }, + u'devel.masterkey': { + 'Meta': {'ordering': "('created',)", 'object_name': 'MasterKey'}, + 'created': ('django.db.models.fields.DateField', [], {}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'owner': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'masterkey_owner'", 'to': u"orm['auth.User']"}), + 'pgp_key': ('devel.fields.PGPKeyField', [], {'max_length': '40'}), + 'revoked': ('django.db.models.fields.DateField', [], {'null': 'True', 'blank': 'True'}), + 'revoker': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'masterkey_revoker'", 'to': u"orm['auth.User']"}) + }, + u'devel.pgpsignature': { + 'Meta': {'ordering': "('signer', 'signee')", 'object_name': 'PGPSignature'}, + 'created': ('django.db.models.fields.DateField', [], {}), + 'expires': ('django.db.models.fields.DateField', [], {'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'revoked': ('django.db.models.fields.DateField', [], {'null': 'True', 'blank': 'True'}), + 'signee': ('devel.fields.PGPKeyField', [], {'max_length': '40', 'db_index': 'True'}), + 'signer': ('devel.fields.PGPKeyField', [], {'max_length': '40', 'db_index': 'True'}) + }, + u'devel.userprofile': { + 'Meta': {'object_name': 'UserProfile', 'db_table': "'user_profiles'"}, + 'alias': ('django.db.models.fields.CharField', [], {'max_length': '50'}), + 'allowed_repos': ('django.db.models.fields.related.ManyToManyField', [], {'to': u"orm['main.Repo']", 'symmetrical': 'False', 'blank': 'True'}), + 'country': ('django_countries.fields.CountryField', [], {'max_length': '2', 'blank': 'True'}), + 'favorite_distros': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'interests': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True', 'blank': 'True'}), + 'languages': ('django.db.models.fields.CharField', [], {'max_length': '50', 'null': 'True', 'blank': 'True'}), + 'last_modified': ('django.db.models.fields.DateTimeField', [], {}), + 'latin_name': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True', 'blank': 'True'}), + 'location': ('django.db.models.fields.CharField', [], {'max_length': '50', 'null': 'True', 'blank': 'True'}), + 'notify': ('django.db.models.fields.BooleanField', [], {'default': 'True'}), + 'occupation': ('django.db.models.fields.CharField', [], {'max_length': '50', 'null': 'True', 'blank': 'True'}), + 'other_contact': ('django.db.models.fields.CharField', [], {'max_length': '100', 'null': 'True', 'blank': 'True'}), + 'pgp_key': ('devel.fields.PGPKeyField', [], {'max_length': '40', 'null': 'True', 'blank': 'True'}), + 'picture': ('django.db.models.fields.files.FileField', [], {'default': "'devs/silhouette.png'", 'max_length': '100'}), + 'public_email': ('django.db.models.fields.CharField', [], {'max_length': '50'}), + 'roles': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True', 'blank': 'True'}), + 'time_zone': ('django.db.models.fields.CharField', [], {'default': "'UTC'", 'max_length': '100'}), + 'user': ('django.db.models.fields.related.OneToOneField', [], {'related_name': "'userprofile'", 'unique': 'True', 'to': u"orm['auth.User']"}), + 'website': ('django.db.models.fields.CharField', [], {'max_length': '200', 'null': 'True', 'blank': 'True'}), + 'yob': ('django.db.models.fields.IntegerField', [], {'null': 'True', 'blank': 'True'}) + }, + u'main.repo': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Repo', 'db_table': "'repos'"}, + 'bugs_category': ('django.db.models.fields.SmallIntegerField', [], {'default': '2'}), + 'bugs_project': ('django.db.models.fields.SmallIntegerField', [], {'default': '1'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'staging': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'svn_root': ('django.db.models.fields.CharField', [], {'max_length': '64'}), + 'testing': ('django.db.models.fields.BooleanField', [], {'default': 'False'}) + } + } + + complete_apps = ['devel'] diff --git a/devel/models.py b/devel/models.py index bf979338..44bbc66e 100644 --- a/devel/models.py +++ b/devel/models.py @@ -107,7 +107,7 @@ class PGPSignature(models.Model): db_index=True) created = models.DateField() expires = models.DateField(null=True, blank=True) - valid = models.BooleanField(default=True) + revoked = models.DateField(null=True, blank=True) class Meta: ordering = ('signer', 'signee') diff --git a/public/views.py b/public/views.py index 24edd044..f79c8f32 100644 --- a/public/views.py +++ b/public/views.py @@ -126,7 +126,7 @@ def keys(request): 'owner__userprofile', 'revoker__userprofile').filter( revoked__isnull=True) - sig_counts = PGPSignature.objects.filter(not_expired, valid=True, + sig_counts = PGPSignature.objects.filter(not_expired, revoked__isnull=True, signee__in=user_key_ids).order_by().values_list('signer').annotate( Count('signer')) sig_counts = {key_id[-16:]: ct for key_id, ct in sig_counts} @@ -136,11 +136,11 @@ def keys(request): # frozenset because we are going to do lots of __contains__ lookups signatures = frozenset(PGPSignature.objects.filter( - not_expired, valid=True).values_list('signer', 'signee')) + not_expired, revoked__isnull=True).values_list('signer', 'signee')) restrict = Q(signer__in=user_key_ids) & Q(signee__in=user_key_ids) cross_signatures = PGPSignature.objects.filter(restrict, - not_expired, valid=True).order_by('created') + not_expired, revoked__isnull=True).order_by('created') context = { 'keys': master_keys, @@ -183,7 +183,7 @@ def keys_json(request): }) not_expired = Q(expires__gt=datetime.utcnow) | Q(expires__isnull=True) - signatures = PGPSignature.objects.filter(not_expired, valid=True) + signatures = PGPSignature.objects.filter(not_expired, revoked__isnull=True) edge_list = [{ 'signee': sig.signee, 'signer': sig.signer } for sig in signatures] -- cgit v1.2.3-54-g00ecf From 5d22a3b891be36b74871b88cb1b125723996415e Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Sun, 27 Oct 2013 11:54:32 -0500 Subject: Bump requirements --- requirements.txt | 6 +++--- requirements_prod.txt | 6 +++--- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/requirements.txt b/requirements.txt index 53aaa05c..479c2134 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,10 +1,10 @@ -e git+git://github.com/fredj/cssmin.git@master#egg=cssmin -Django==1.5.4 +Django==1.5.5 IPy==0.81 Markdown==2.3.1 South==0.8.2 bencode==1.0 django-countries==1.5 -jsmin==2.0.4 +jsmin==2.0.6 pgpdump==1.4 -pytz>=2013b +pytz>=2013.7 diff --git a/requirements_prod.txt b/requirements_prod.txt index 7cc19970..2c38903e 100644 --- a/requirements_prod.txt +++ b/requirements_prod.txt @@ -1,13 +1,13 @@ -e git+git://github.com/fredj/cssmin.git@master#egg=cssmin -Django==1.5.4 +Django==1.5.5 IPy==0.81 Markdown==2.3.1 South==0.8.2 bencode==1.0 django-countries==1.5 -jsmin==2.0.4 +jsmin==2.0.6 pgpdump==1.4 psycopg2==2.5.1 pyinotify==0.9.4 python-memcached==1.53 -pytz>=2013b +pytz>=2013.7 -- cgit v1.2.3-54-g00ecf From 7ac017e1e7884320bd00f67134dd1ae7e06ceaaf Mon Sep 17 00:00:00 2001 From: Dario Giovannetti Date: Sun, 3 Nov 2013 13:15:05 +0800 Subject: Remove "Unofficial" from Beginners' Guide link Also avoid internal redirect to the Installation Guide article. Fixes FS#36111. Dan: remove "Official" from install guide link text as well to match wiki page name. --- templates/public/index.html | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/templates/public/index.html b/templates/public/index.html index 7e6daf8d..c5924ab7 100644 --- a/templates/public/index.html +++ b/templates/public/index.html @@ -112,10 +112,10 @@

Documentation

Community

-- cgit v1.2.3-54-g00ecf From 5943f92e4c6d52bec6a1e68ad11970da9b8ad643 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 20:33:55 -0600 Subject: Fix parsing of depends with both epoch and description Not a common case, but one we can and should support and hasn't been noticed up until this point. That pesky colon! Fixes FS#37477. Signed-off-by: Dan McGee --- devel/management/commands/reporead.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/devel/management/commands/reporead.py b/devel/management/commands/reporead.py index a0e77dc7..ff7a8427 100644 --- a/devel/management/commands/reporead.py +++ b/devel/management/commands/reporead.py @@ -138,8 +138,8 @@ def full_version(self): def create_depend(package, dep_str, deptype='D'): depend = Depend(pkg=package, deptype=deptype) - # lop off any description first - parts = dep_str.split(':', 1) + # lop off any description first, don't get confused by epoch + parts = dep_str.split(': ', 1) if len(parts) > 1: depend.description = parts[1].strip() match = DEPEND_RE.match(parts[0].strip()) -- cgit v1.2.3-54-g00ecf From d54df175a89385e50193447d02e6842e28c24f7d Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 20:55:05 -0600 Subject: Django 1.6 upgrade, deprecation cleanup PendingDeprecationWarning: `queryset` method should be renamed `get_queryset` Signed-off-by: Dan McGee --- packages/admin.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/admin.py b/packages/admin.py index 820bbb29..4680c755 100644 --- a/packages/admin.py +++ b/packages/admin.py @@ -20,7 +20,7 @@ class FlagRequestAdmin(admin.ModelAdmin): ordering = ('-created',) date_hierarchy = 'created' - def queryset(self, request): + def get_queryset(self, request): qs = super(FlagRequestAdmin, self).queryset(request) return qs.select_related('repo', 'user') @@ -42,7 +42,7 @@ class SignoffSpecificationAdmin(admin.ModelAdmin): ordering = ('-created',) date_hierarchy = 'created' - def queryset(self, request): + def get_queryset(self, request): qs = super(SignoffSpecificationAdmin, self).queryset(request) return qs.select_related('arch', 'repo', 'user') -- cgit v1.2.3-54-g00ecf From 3061d1c9515cd44ecc79f95c57b268564a481ccf Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 20:56:15 -0600 Subject: Django 1.6 upgrade, deprecation cleanup PendingDeprecationWarning: Creating a ModelForm without either the 'fields' attribute or the 'exclude' attribute is deprecated - form needs updating Signed-off-by: Dan McGee --- mirrors/admin.py | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/mirrors/admin.py b/mirrors/admin.py index d0f2f475..e35d9ce7 100644 --- a/mirrors/admin.py +++ b/mirrors/admin.py @@ -10,6 +10,7 @@ class MirrorUrlForm(forms.ModelForm): class Meta: model = MirrorUrl + fields = ('url', 'country', 'active') def clean_url(self): # is this a valid-looking URL? @@ -39,6 +40,7 @@ class MirrorUrlInlineAdmin(admin.TabularInline): class MirrorRsyncForm(forms.ModelForm): class Meta: model = MirrorRsync + fields = ('ip',) class MirrorRsyncInlineAdmin(admin.TabularInline): @@ -50,6 +52,10 @@ class MirrorRsyncInlineAdmin(admin.TabularInline): class MirrorAdminForm(forms.ModelForm): class Meta: model = Mirror + fields = ('name', 'tier', 'upstream', 'admin_email', 'alternate_email', + 'public', 'active', 'isos', 'rsync_user', 'rsync_password', + 'notes') + upstream = forms.ModelChoiceField( queryset=Mirror.objects.filter(tier__gte=0, tier__lte=1), required=False) -- cgit v1.2.3-54-g00ecf From 86f9d6788e22376560ca1a56e86c8f679b832907 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 21:10:52 -0600 Subject: Django 1.6 upgrade, deprecation cleanup PendingDeprecationWarning: 'The `cycle` template tag is changing to escape its arguments; the non-autoescaping version is deprecated. Load it from the `future` tag library to start using the new behavior. Signed-off-by: Dan McGee --- templates/devel/clock.html | 1 + templates/devel/index.html | 1 + templates/devel/packages.html | 1 + templates/devel/stats.html | 1 + templates/mirrors/error_table.html | 1 + templates/mirrors/mirror_details.html | 1 + templates/mirrors/mirrors.html | 1 + templates/mirrors/status_table.html | 1 + templates/news/list.html | 2 ++ templates/packages/differences.html | 1 + templates/packages/groups.html | 1 + templates/packages/packages_list.html | 1 + templates/packages/search.html | 1 + templates/packages/signoffs.html | 1 + templates/packages/stale_relations.html | 1 + templates/releng/release_list.html | 1 + templates/todolists/list.html | 1 + templates/todolists/view.html | 1 + 18 files changed, 19 insertions(+) diff --git a/templates/devel/clock.html b/templates/devel/clock.html index 2c5bfacf..9d672f12 100644 --- a/templates/devel/clock.html +++ b/templates/devel/clock.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% load flags %} {% load tz %} diff --git a/templates/devel/index.html b/templates/devel/index.html index 03e5d73a..c0c437a6 100644 --- a/templates/devel/index.html +++ b/templates/devel/index.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% load cache %} {% load package_extras %} diff --git a/templates/devel/packages.html b/templates/devel/packages.html index d6aab497..74aebf20 100644 --- a/templates/devel/packages.html +++ b/templates/devel/packages.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% load attributes %} {% load package_extras %} diff --git a/templates/devel/stats.html b/templates/devel/stats.html index 2dbe4755..9b3b1d28 100644 --- a/templates/devel/stats.html +++ b/templates/devel/stats.html @@ -1,3 +1,4 @@ +{% load cycle from future %} {% load cache %} {% cache 60 dev-dash-by-arch %} diff --git a/templates/mirrors/error_table.html b/templates/mirrors/error_table.html index 6054814f..cd7265af 100644 --- a/templates/mirrors/error_table.html +++ b/templates/mirrors/error_table.html @@ -1,3 +1,4 @@ +{% load cycle from future %} {% load flags mirror_status %} diff --git a/templates/mirrors/mirror_details.html b/templates/mirrors/mirror_details.html index 1c7f5633..f2ffce20 100644 --- a/templates/mirrors/mirror_details.html +++ b/templates/mirrors/mirror_details.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% load mirror_status %} {% load flags %} diff --git a/templates/mirrors/mirrors.html b/templates/mirrors/mirrors.html index 458b693f..4276b30a 100644 --- a/templates/mirrors/mirrors.html +++ b/templates/mirrors/mirrors.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% block title %}Arch Linux - Mirror Overview{% endblock %} diff --git a/templates/mirrors/status_table.html b/templates/mirrors/status_table.html index 28175420..6fc07a31 100644 --- a/templates/mirrors/status_table.html +++ b/templates/mirrors/status_table.html @@ -1,3 +1,4 @@ +{% load cycle from future %} {% load flags mirror_status %}
diff --git a/templates/news/list.html b/templates/news/list.html index e85ceced..4acbc7e9 100644 --- a/templates/news/list.html +++ b/templates/news/list.html @@ -1,4 +1,6 @@ {% extends "base.html" %} +{% load cycle from future %} + {% block title %}Arch Linux - News{% endblock %} {% block head %} diff --git a/templates/packages/differences.html b/templates/packages/differences.html index b0b9b419..f137126d 100644 --- a/templates/packages/differences.html +++ b/templates/packages/differences.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% block title %}Arch Linux - Package Differences Reports{% endblock %} diff --git a/templates/packages/groups.html b/templates/packages/groups.html index c135791f..ee4f0312 100644 --- a/templates/packages/groups.html +++ b/templates/packages/groups.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% block title %}Arch Linux - Package Groups{% if arch %} - {{ arch }}{% endif %}{% endblock %} diff --git a/templates/packages/packages_list.html b/templates/packages/packages_list.html index 3dcc03dc..0a1627f8 100644 --- a/templates/packages/packages_list.html +++ b/templates/packages/packages_list.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% load package_extras %} diff --git a/templates/packages/search.html b/templates/packages/search.html index f50bc8be..d312c374 100644 --- a/templates/packages/search.html +++ b/templates/packages/search.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load package_extras %} {% block title %}Arch Linux - Package Database{% endblock %} diff --git a/templates/packages/signoffs.html b/templates/packages/signoffs.html index 807b613b..83f81d39 100644 --- a/templates/packages/signoffs.html +++ b/templates/packages/signoffs.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% load package_extras %} diff --git a/templates/packages/stale_relations.html b/templates/packages/stale_relations.html index 14fac397..76f32052 100644 --- a/templates/packages/stale_relations.html +++ b/templates/packages/stale_relations.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% block title %}Arch Linux - Stale Package Relations{% endblock %} diff --git a/templates/releng/release_list.html b/templates/releng/release_list.html index 7197cc8d..f7e90377 100644 --- a/templates/releng/release_list.html +++ b/templates/releng/release_list.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% block title %}Arch Linux - Releases{% endblock %} diff --git a/templates/todolists/list.html b/templates/todolists/list.html index 56f9874d..7f0368de 100644 --- a/templates/todolists/list.html +++ b/templates/todolists/list.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% block title %}Arch Linux - Todo Lists{% endblock %} diff --git a/templates/todolists/view.html b/templates/todolists/view.html index b26cd91c..a3ee5479 100644 --- a/templates/todolists/view.html +++ b/templates/todolists/view.html @@ -1,4 +1,5 @@ {% extends "base.html" %} +{% load cycle from future %} {% load static from staticfiles %} {% load package_extras %} {% load todolists %} -- cgit v1.2.3-54-g00ecf From ee6002c911952ddc8cfd07fded3de2c9b0193dc6 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 21:17:27 -0600 Subject: Django 1.6 upgrade, deprecation cleanup PendingDeprecationWarning: commit_on_success is deprecated in favor of atomic. Signed-off-by: Dan McGee --- devel/management/commands/pgp_import.py | 4 ++-- devel/management/commands/rematch_developers.py | 4 ++-- devel/management/commands/reporead.py | 10 +++++----- devel/management/commands/reporead_inotify.py | 2 +- devel/views.py | 4 ++-- mirrors/management/commands/mirrorcheck.py | 2 +- packages/views/flag.py | 2 +- packages/views/signoff.py | 2 +- todolists/views.py | 2 +- 9 files changed, 16 insertions(+), 16 deletions(-) diff --git a/devel/management/commands/pgp_import.py b/devel/management/commands/pgp_import.py index faa9ff5e..3f557fe9 100644 --- a/devel/management/commands/pgp_import.py +++ b/devel/management/commands/pgp_import.py @@ -134,7 +134,7 @@ def import_keys(keyring): logger.info("creating or finding %d keys", len(keydata)) created_ct = updated_ct = 0 - with transaction.commit_on_success(): + with transaction.atomic(): finder = UserFinder() # we are dependent on parents coming before children; parse_keydata # uses an OrderedDict to ensure this is the case. @@ -232,7 +232,7 @@ def import_signatures(keyring): logger.info("creating or finding up to %d signatures", len(pruned_edges)) created_ct = updated_ct = 0 - with transaction.commit_on_success(): + with transaction.atomic(): for edge in pruned_edges: sig, created = PGPSignature.objects.get_or_create( signer=edge.signer, signee=edge.signee, diff --git a/devel/management/commands/rematch_developers.py b/devel/management/commands/rematch_developers.py index 2b379588..7a06e084 100644 --- a/devel/management/commands/rematch_developers.py +++ b/devel/management/commands/rematch_developers.py @@ -44,7 +44,7 @@ def handle_noargs(self, **options): match_packager(finder) match_flagrequest(finder) -@transaction.commit_on_success +@transaction.atomic def match_packager(finder): logger.info("getting all unmatched packager strings") package_count = matched_count = 0 @@ -70,7 +70,7 @@ def match_packager(finder): package_count, matched_count) -@transaction.commit_on_success +@transaction.atomic def match_flagrequest(finder): logger.info("getting all flag request email addresses from unknown users") req_count = matched_count = 0 diff --git a/devel/management/commands/reporead.py b/devel/management/commands/reporead.py index ff7a8427..19d54e1e 100644 --- a/devel/management/commands/reporead.py +++ b/devel/management/commands/reporead.py @@ -302,7 +302,7 @@ def update_common(archname, reponame, pkgs, sanity_check=True): # If isolation level is repeatable-read, we need to ensure each package # update starts a new transaction and re-queries the database as # necessary to guard against simultaneous updates. - with transaction.commit_on_success(): + with transaction.atomic(): # force the transaction dirty, even though we will only do reads transaction.set_dirty() @@ -365,7 +365,7 @@ def db_update(archname, reponame, pkgs, force=False): dbpkg = Package(pkgname=pkg.name, arch=architecture, repo=repository, created=timestamp) try: - with transaction.commit_on_success(): + with transaction.atomic(): populate_pkg(dbpkg, pkg, timestamp=timestamp) Update.objects.log_update(None, dbpkg) except IntegrityError: @@ -380,7 +380,7 @@ def db_update(archname, reponame, pkgs, force=False): for pkgname in (dbset - syncset): logger.info("Removing package %s", pkgname) dbpkg = dbdict[pkgname] - with transaction.commit_on_success(): + with transaction.atomic(): Update.objects.log_update(dbpkg, None) # no race condition here as long as simultaneous threads both # issue deletes; second delete will be a no-op @@ -403,7 +403,7 @@ def db_update(archname, reponame, pkgs, force=False): # The odd select_for_update song and dance here are to ensure # simultaneous updates don't happen on a package, causing # files/depends/all related items to be double-imported. - with transaction.commit_on_success(): + with transaction.atomic(): dbpkg = Package.objects.select_for_update().get(id=dbpkg.id) if not force and pkg_same_version(pkg, dbpkg): logger.debug("Package %s was already updated", pkg.name) @@ -431,7 +431,7 @@ def filesonly_update(archname, reponame, pkgs, force=False): # The odd select_for_update song and dance here are to ensure # simultaneous updates don't happen on a package, causing # files to be double-imported. - with transaction.commit_on_success(): + with transaction.atomic(): if not dbpkg.files_last_update or not dbpkg.last_update: pass elif not force and dbpkg.files_last_update >= dbpkg.last_update: diff --git a/devel/management/commands/reporead_inotify.py b/devel/management/commands/reporead_inotify.py index 6aa4e0e0..e3c720bc 100644 --- a/devel/management/commands/reporead_inotify.py +++ b/devel/management/commands/reporead_inotify.py @@ -66,7 +66,7 @@ def handle(self, path_template=None, **options): if hasattr(thread, 'cancel'): thread.cancel() - @transaction.commit_on_success + @transaction.atomic def setup_notifier(self): '''Set up and configure the inotify machinery and logic. This takes the provided or default path_template and builds a list of diff --git a/devel/views.py b/devel/views.py index 378d6d57..fe7fdf8c 100644 --- a/devel/views.py +++ b/devel/views.py @@ -166,7 +166,7 @@ def change_profile(request): request.user.email = form.cleaned_data['email'] if form.cleaned_data['passwd1']: request.user.set_password(form.cleaned_data['passwd1']) - with transaction.commit_on_success(): + with transaction.atomic(): request.user.save() profile_form.save() return HttpResponseRedirect('/devel/') @@ -334,7 +334,7 @@ def new_user_form(request): if request.POST: form = NewUserForm(request.POST) if form.is_valid(): - with transaction.commit_on_success(): + with transaction.atomic(): form.save() log_addition(request, form.instance.user) return HttpResponseRedirect('/admin/auth/user/%d/' % \ diff --git a/mirrors/management/commands/mirrorcheck.py b/mirrors/management/commands/mirrorcheck.py index 3f026c36..e48aa42e 100644 --- a/mirrors/management/commands/mirrorcheck.py +++ b/mirrors/management/commands/mirrorcheck.py @@ -241,7 +241,7 @@ def __init__(self, urls, location, timeout=10, num_threads=10): thread.daemon = True self.threads.append(thread) - @transaction.commit_on_success + @transaction.atomic def run(self): logger.debug("starting threads") for thread in self.threads: diff --git a/packages/views/flag.py b/packages/views/flag.py index 39cdcef8..9fe60e2c 100644 --- a/packages/views/flag.py +++ b/packages/views/flag.py @@ -84,7 +84,7 @@ def flag(request, name, repo, arch): else: email = form.cleaned_data['email'] - @transaction.commit_on_success + @transaction.atomic def perform_updates(): current_time = now() pkgs.update(flag_date=current_time) diff --git a/packages/views/signoff.py b/packages/views/signoff.py index c37aa0fc..fcc6de45 100644 --- a/packages/views/signoff.py +++ b/packages/views/signoff.py @@ -81,7 +81,7 @@ class Meta: def _signoff_options_all(request, name, repo): seen_ids = set() - with transaction.commit_on_success(): + with transaction.atomic(): # find or create a specification for all architectures, then # graft the form data onto them packages = Package.objects.filter(pkgbase=name, diff --git a/todolists/views.py b/todolists/views.py index ff75686d..c37c13f5 100644 --- a/todolists/views.py +++ b/todolists/views.py @@ -147,7 +147,7 @@ class DeleteTodolist(DeleteView): success_url = '/todo/' -@transaction.commit_on_success +@transaction.atomic def create_todolist_packages(form, creator=None): package_names = form.package_names() packages = form.packages() -- cgit v1.2.3-54-g00ecf From b45700ffe841004af5943c683e0bb0c8f0877015 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 21:35:32 -0600 Subject: Bump requirements versions for Django 1.6 Signed-off-by: Dan McGee --- requirements.txt | 4 ++-- requirements_prod.txt | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/requirements.txt b/requirements.txt index 479c2134..08d89107 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,5 +1,5 @@ -e git+git://github.com/fredj/cssmin.git@master#egg=cssmin -Django==1.5.5 +Django==1.6 IPy==0.81 Markdown==2.3.1 South==0.8.2 @@ -7,4 +7,4 @@ bencode==1.0 django-countries==1.5 jsmin==2.0.6 pgpdump==1.4 -pytz>=2013.7 +pytz>=2013.8 diff --git a/requirements_prod.txt b/requirements_prod.txt index 2c38903e..565c3c6c 100644 --- a/requirements_prod.txt +++ b/requirements_prod.txt @@ -1,5 +1,5 @@ -e git+git://github.com/fredj/cssmin.git@master#egg=cssmin -Django==1.5.5 +Django==1.6 IPy==0.81 Markdown==2.3.1 South==0.8.2 @@ -10,4 +10,4 @@ pgpdump==1.4 psycopg2==2.5.1 pyinotify==0.9.4 python-memcached==1.53 -pytz>=2013.7 +pytz>=2013.8 -- cgit v1.2.3-54-g00ecf From cf27baf51956747f9ea5a349d41e796031871c5c Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 21:48:52 -0600 Subject: Add new `signature_bytes` field on package model Now that we have a BinaryField option in Django 1.6, put it to use. Signed-off-by: Dan McGee --- ...0065_auto__add_field_package_signature_bytes.py | 115 +++++++++++++++++++++ main/models.py | 7 +- 2 files changed, 119 insertions(+), 3 deletions(-) create mode 100644 main/migrations/0065_auto__add_field_package_signature_bytes.py diff --git a/main/migrations/0065_auto__add_field_package_signature_bytes.py b/main/migrations/0065_auto__add_field_package_signature_bytes.py new file mode 100644 index 00000000..95c596c1 --- /dev/null +++ b/main/migrations/0065_auto__add_field_package_signature_bytes.py @@ -0,0 +1,115 @@ +# -*- coding: utf-8 -*- +import datetime +from south.db import db +from south.v2 import SchemaMigration +from django.db import models + + +class Migration(SchemaMigration): + + def forwards(self, orm): + db.add_column('packages', 'signature_bytes', + self.gf('django.db.models.fields.BinaryField')(null=True), + keep_default=True) + + def backwards(self, orm): + db.delete_column('packages', 'signature_bytes') + + + models = { + u'auth.group': { + 'Meta': {'object_name': 'Group'}, + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '80'}), + 'permissions': ('django.db.models.fields.related.ManyToManyField', [], {'to': u"orm['auth.Permission']", 'symmetrical': 'False', 'blank': 'True'}) + }, + u'auth.permission': { + 'Meta': {'ordering': "(u'content_type__app_label', u'content_type__model', u'codename')", 'unique_together': "((u'content_type', u'codename'),)", 'object_name': 'Permission'}, + 'codename': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'content_type': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['contenttypes.ContentType']"}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '50'}) + }, + u'auth.user': { + 'Meta': {'object_name': 'User'}, + 'date_joined': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'email': ('django.db.models.fields.EmailField', [], {'max_length': '75', 'blank': 'True'}), + 'first_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'groups': ('django.db.models.fields.related.ManyToManyField', [], {'symmetrical': 'False', 'related_name': "u'user_set'", 'blank': 'True', 'to': u"orm['auth.Group']"}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'is_active': ('django.db.models.fields.BooleanField', [], {'default': 'True'}), + 'is_staff': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'is_superuser': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'last_login': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'last_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'password': ('django.db.models.fields.CharField', [], {'max_length': '128'}), + 'user_permissions': ('django.db.models.fields.related.ManyToManyField', [], {'symmetrical': 'False', 'related_name': "u'user_set'", 'blank': 'True', 'to': u"orm['auth.Permission']"}), + 'username': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '30'}) + }, + u'contenttypes.contenttype': { + 'Meta': {'ordering': "('name',)", 'unique_together': "(('app_label', 'model'),)", 'object_name': 'ContentType', 'db_table': "'django_content_type'"}, + 'app_label': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'model': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '100'}) + }, + u'main.arch': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Arch', 'db_table': "'arches'"}, + 'agnostic': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'required_signoffs': ('django.db.models.fields.PositiveIntegerField', [], {'default': '2'}) + }, + u'main.donor': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Donor', 'db_table': "'donors'"}, + 'created': ('django.db.models.fields.DateTimeField', [], {}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'visible': ('django.db.models.fields.BooleanField', [], {'default': 'True'}) + }, + u'main.package': { + 'Meta': {'ordering': "('pkgname',)", 'unique_together': "(('pkgname', 'repo', 'arch'),)", 'object_name': 'Package', 'db_table': "'packages'"}, + 'arch': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'packages'", 'on_delete': 'models.PROTECT', 'to': u"orm['main.Arch']"}), + 'build_date': ('django.db.models.fields.DateTimeField', [], {'null': 'True'}), + 'compressed_size': ('main.fields.PositiveBigIntegerField', [], {}), + 'created': ('django.db.models.fields.DateTimeField', [], {}), + 'epoch': ('django.db.models.fields.PositiveIntegerField', [], {'default': '0'}), + 'filename': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'files_last_update': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}), + 'flag_date': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'installed_size': ('main.fields.PositiveBigIntegerField', [], {}), + 'last_update': ('django.db.models.fields.DateTimeField', [], {'db_index': 'True'}), + 'packager': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['auth.User']", 'null': 'True', 'on_delete': 'models.SET_NULL', 'blank': 'True'}), + 'packager_str': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pgp_signature': ('django.db.models.fields.TextField', [], {'null': 'True', 'blank': 'True'}), + 'pkgbase': ('django.db.models.fields.CharField', [], {'max_length': '255', 'db_index': 'True'}), + 'pkgdesc': ('django.db.models.fields.TextField', [], {'null': 'True'}), + 'pkgname': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pkgrel': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pkgver': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'repo': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'packages'", 'on_delete': 'models.PROTECT', 'to': u"orm['main.Repo']"}), + 'signature_bytes': ('django.db.models.fields.BinaryField', [], {'null': 'True'}), + 'url': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True'}) + }, + u'main.packagefile': { + 'Meta': {'object_name': 'PackageFile', 'db_table': "'package_files'"}, + 'directory': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'filename': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'is_directory': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'pkg': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['main.Package']"}) + }, + u'main.repo': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Repo', 'db_table': "'repos'"}, + 'bugs_category': ('django.db.models.fields.SmallIntegerField', [], {'default': '2'}), + 'bugs_project': ('django.db.models.fields.SmallIntegerField', [], {'default': '1'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'staging': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'svn_root': ('django.db.models.fields.CharField', [], {'max_length': '64'}), + 'testing': ('django.db.models.fields.BooleanField', [], {'default': 'False'}) + } + } + + complete_apps = ['main'] diff --git a/main/models.py b/main/models.py index 2ace0109..91f1483b 100644 --- a/main/models.py +++ b/main/models.py @@ -97,7 +97,7 @@ class Package(models.Model): pkgver = models.CharField(max_length=255) pkgrel = models.CharField(max_length=255) epoch = models.PositiveIntegerField(default=0) - pkgdesc = models.TextField(null=True) + pkgdesc = models.TextField('description', null=True) url = models.CharField(max_length=255, null=True) filename = models.CharField(max_length=255) compressed_size = PositiveBigIntegerField() @@ -106,10 +106,11 @@ class Package(models.Model): last_update = models.DateTimeField(db_index=True) files_last_update = models.DateTimeField(null=True, blank=True) created = models.DateTimeField() - packager_str = models.CharField(max_length=255) + packager_str = models.CharField('packager string', max_length=255) packager = models.ForeignKey(User, null=True, blank=True, on_delete=models.SET_NULL) - pgp_signature = models.TextField(null=True, blank=True) + pgp_signature = models.TextField('PGP signature', null=True, blank=True) + signature_bytes = models.BinaryField('PGP signature', null=True) flag_date = models.DateTimeField(null=True, blank=True) objects = PackageManager() -- cgit v1.2.3-54-g00ecf From a4cf77ba247605fb442b314e311de2829bb3706b Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 22:05:18 -0600 Subject: Move signature data from base64 string to bytes type Signed-off-by: Dan McGee --- devel/management/commands/reporead.py | 3 +- main/migrations/0066_move_signature_data.py | 125 ++++++++++++++++++++++++++++ main/models.py | 9 +- 3 files changed, 129 insertions(+), 8 deletions(-) create mode 100644 main/migrations/0066_move_signature_data.py diff --git a/devel/management/commands/reporead.py b/devel/management/commands/reporead.py index 19d54e1e..2b565cfc 100644 --- a/devel/management/commands/reporead.py +++ b/devel/management/commands/reporead.py @@ -13,6 +13,7 @@ ./manage.py reporead i686 /tmp/core.db.tar.gz """ +from base64 import b64decode from collections import defaultdict from copy import copy import io @@ -217,7 +218,7 @@ def populate_pkg(dbpkg, repopkg, force=False, timestamp=None): dbpkg.packager_str = repopkg.packager # attempt to find the corresponding django user for this string dbpkg.packager = finder.find(repopkg.packager) - dbpkg.pgp_signature = repopkg.pgpsig + dbpkg.signature_bytes = b64decode(repopkg.pgpsig.encode('utf-8')) if timestamp: dbpkg.last_update = timestamp diff --git a/main/migrations/0066_move_signature_data.py b/main/migrations/0066_move_signature_data.py new file mode 100644 index 00000000..75fcfa92 --- /dev/null +++ b/main/migrations/0066_move_signature_data.py @@ -0,0 +1,125 @@ +# -*- coding: utf-8 -*- +from south.db import db +from south.v2 import DataMigration +from django.db import models +from base64 import b64decode, b64encode + +class Migration(DataMigration): + + def forwards(self, orm): + pkgs = orm.Package.objects.only( + 'id', 'pgp_signature', 'signature_bytes').all() + for pkg in pkgs: + if not pkg.pgp_signature: + continue + pkg.signature_bytes = b64decode(pkg.pgp_signature.encode('utf-8')) + pkg.save() + + def backwards(self, orm): + pkgs = orm.Package.objects.only( + 'id', 'pgp_signature', 'signature_bytes').all() + for pkg in pkgs: + if not pkg.signature_bytes: + continue + pkg.pgp_signature = b64encode(pkg.signature_bytes).decode('utf-8') + pkg.save() + + + models = { + u'auth.group': { + 'Meta': {'object_name': 'Group'}, + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '80'}), + 'permissions': ('django.db.models.fields.related.ManyToManyField', [], {'to': u"orm['auth.Permission']", 'symmetrical': 'False', 'blank': 'True'}) + }, + u'auth.permission': { + 'Meta': {'ordering': "(u'content_type__app_label', u'content_type__model', u'codename')", 'unique_together': "((u'content_type', u'codename'),)", 'object_name': 'Permission'}, + 'codename': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'content_type': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['contenttypes.ContentType']"}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '50'}) + }, + u'auth.user': { + 'Meta': {'object_name': 'User'}, + 'date_joined': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'email': ('django.db.models.fields.EmailField', [], {'max_length': '75', 'blank': 'True'}), + 'first_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'groups': ('django.db.models.fields.related.ManyToManyField', [], {'symmetrical': 'False', 'related_name': "u'user_set'", 'blank': 'True', 'to': u"orm['auth.Group']"}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'is_active': ('django.db.models.fields.BooleanField', [], {'default': 'True'}), + 'is_staff': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'is_superuser': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'last_login': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'last_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'password': ('django.db.models.fields.CharField', [], {'max_length': '128'}), + 'user_permissions': ('django.db.models.fields.related.ManyToManyField', [], {'symmetrical': 'False', 'related_name': "u'user_set'", 'blank': 'True', 'to': u"orm['auth.Permission']"}), + 'username': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '30'}) + }, + u'contenttypes.contenttype': { + 'Meta': {'ordering': "('name',)", 'unique_together': "(('app_label', 'model'),)", 'object_name': 'ContentType', 'db_table': "'django_content_type'"}, + 'app_label': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'model': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '100'}) + }, + u'main.arch': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Arch', 'db_table': "'arches'"}, + 'agnostic': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'required_signoffs': ('django.db.models.fields.PositiveIntegerField', [], {'default': '2'}) + }, + u'main.donor': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Donor', 'db_table': "'donors'"}, + 'created': ('django.db.models.fields.DateTimeField', [], {}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'visible': ('django.db.models.fields.BooleanField', [], {'default': 'True'}) + }, + u'main.package': { + 'Meta': {'ordering': "('pkgname',)", 'unique_together': "(('pkgname', 'repo', 'arch'),)", 'object_name': 'Package', 'db_table': "'packages'"}, + 'arch': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'packages'", 'on_delete': 'models.PROTECT', 'to': u"orm['main.Arch']"}), + 'build_date': ('django.db.models.fields.DateTimeField', [], {'null': 'True'}), + 'compressed_size': ('main.fields.PositiveBigIntegerField', [], {}), + 'created': ('django.db.models.fields.DateTimeField', [], {}), + 'epoch': ('django.db.models.fields.PositiveIntegerField', [], {'default': '0'}), + 'filename': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'files_last_update': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}), + 'flag_date': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'installed_size': ('main.fields.PositiveBigIntegerField', [], {}), + 'last_update': ('django.db.models.fields.DateTimeField', [], {'db_index': 'True'}), + 'packager': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['auth.User']", 'null': 'True', 'on_delete': 'models.SET_NULL', 'blank': 'True'}), + 'packager_str': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pgp_signature': ('django.db.models.fields.TextField', [], {'null': 'True', 'blank': 'True'}), + 'pkgbase': ('django.db.models.fields.CharField', [], {'max_length': '255', 'db_index': 'True'}), + 'pkgdesc': ('django.db.models.fields.TextField', [], {'null': 'True'}), + 'pkgname': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pkgrel': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pkgver': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'repo': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'packages'", 'on_delete': 'models.PROTECT', 'to': u"orm['main.Repo']"}), + 'signature_bytes': ('django.db.models.fields.BinaryField', [], {'null': 'True'}), + 'url': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True'}) + }, + u'main.packagefile': { + 'Meta': {'object_name': 'PackageFile', 'db_table': "'package_files'"}, + 'directory': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'filename': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'is_directory': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'pkg': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['main.Package']"}) + }, + u'main.repo': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Repo', 'db_table': "'repos'"}, + 'bugs_category': ('django.db.models.fields.SmallIntegerField', [], {'default': '2'}), + 'bugs_project': ('django.db.models.fields.SmallIntegerField', [], {'default': '1'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'staging': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'svn_root': ('django.db.models.fields.CharField', [], {'max_length': '64'}), + 'testing': ('django.db.models.fields.BooleanField', [], {'default': 'False'}) + } + } + + complete_apps = ['main'] + symmetrical = True diff --git a/main/models.py b/main/models.py index 91f1483b..70872c60 100644 --- a/main/models.py +++ b/main/models.py @@ -1,4 +1,3 @@ -from base64 import b64decode from datetime import datetime from itertools import groupby from pgpdump import BinaryData @@ -141,13 +140,9 @@ def get_full_url(self, proto='https'): @property def signature(self): - try: - data = b64decode(self.pgp_signature.encode('utf-8')) - except TypeError: - return None - if not data: + if not self.signature_bytes: return None - data = BinaryData(data) + data = BinaryData(self.signature_bytes) packets = list(data.packets()) return packets[0] -- cgit v1.2.3-54-g00ecf From 071bd6bd71f681c45048fc0a0961e58d43d44d48 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Wed, 6 Nov 2013 22:08:01 -0600 Subject: Drop old base64-ed PGP signature column We've moved onto bytes only now. Signed-off-by: Dan McGee --- devel/views.py | 2 +- ...0065_auto__add_field_package_signature_bytes.py | 1 - .../0067_auto__del_field_package_pgp_signature.py | 113 +++++++++++++++++++++ main/models.py | 1 - 4 files changed, 114 insertions(+), 3 deletions(-) create mode 100644 main/migrations/0067_auto__del_field_package_pgp_signature.py diff --git a/devel/views.py b/devel/views.py index fe7fdf8c..731827f3 100644 --- a/devel/views.py +++ b/devel/views.py @@ -274,7 +274,7 @@ def report(request, report_name, username=None): cutoff = timedelta(hours=24) filtered = [] packages = packages.select_related( - 'arch', 'repo', 'packager').filter(pgp_signature__isnull=False) + 'arch', 'repo', 'packager').filter(signature_bytes__isnull=False) known_keys = DeveloperKey.objects.select_related( 'owner').filter(owner__isnull=False) known_keys = {dk.key: dk for dk in known_keys} diff --git a/main/migrations/0065_auto__add_field_package_signature_bytes.py b/main/migrations/0065_auto__add_field_package_signature_bytes.py index 95c596c1..a954166e 100644 --- a/main/migrations/0065_auto__add_field_package_signature_bytes.py +++ b/main/migrations/0065_auto__add_field_package_signature_bytes.py @@ -1,5 +1,4 @@ # -*- coding: utf-8 -*- -import datetime from south.db import db from south.v2 import SchemaMigration from django.db import models diff --git a/main/migrations/0067_auto__del_field_package_pgp_signature.py b/main/migrations/0067_auto__del_field_package_pgp_signature.py new file mode 100644 index 00000000..8c1d9b7a --- /dev/null +++ b/main/migrations/0067_auto__del_field_package_pgp_signature.py @@ -0,0 +1,113 @@ +# -*- coding: utf-8 -*- +from south.db import db +from south.v2 import SchemaMigration +from django.db import models + + +class Migration(SchemaMigration): + + def forwards(self, orm): + db.delete_column('packages', 'pgp_signature') + + def backwards(self, orm): + db.add_column('packages', 'pgp_signature', + self.gf('django.db.models.fields.TextField')(null=True, blank=True), + keep_default=True) + + + models = { + u'auth.group': { + 'Meta': {'object_name': 'Group'}, + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '80'}), + 'permissions': ('django.db.models.fields.related.ManyToManyField', [], {'to': u"orm['auth.Permission']", 'symmetrical': 'False', 'blank': 'True'}) + }, + u'auth.permission': { + 'Meta': {'ordering': "(u'content_type__app_label', u'content_type__model', u'codename')", 'unique_together': "((u'content_type', u'codename'),)", 'object_name': 'Permission'}, + 'codename': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'content_type': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['contenttypes.ContentType']"}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '50'}) + }, + u'auth.user': { + 'Meta': {'object_name': 'User'}, + 'date_joined': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'email': ('django.db.models.fields.EmailField', [], {'max_length': '75', 'blank': 'True'}), + 'first_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'groups': ('django.db.models.fields.related.ManyToManyField', [], {'symmetrical': 'False', 'related_name': "u'user_set'", 'blank': 'True', 'to': u"orm['auth.Group']"}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'is_active': ('django.db.models.fields.BooleanField', [], {'default': 'True'}), + 'is_staff': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'is_superuser': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'last_login': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}), + 'last_name': ('django.db.models.fields.CharField', [], {'max_length': '30', 'blank': 'True'}), + 'password': ('django.db.models.fields.CharField', [], {'max_length': '128'}), + 'user_permissions': ('django.db.models.fields.related.ManyToManyField', [], {'symmetrical': 'False', 'related_name': "u'user_set'", 'blank': 'True', 'to': u"orm['auth.Permission']"}), + 'username': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '30'}) + }, + u'contenttypes.contenttype': { + 'Meta': {'ordering': "('name',)", 'unique_together': "(('app_label', 'model'),)", 'object_name': 'ContentType', 'db_table': "'django_content_type'"}, + 'app_label': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'model': ('django.db.models.fields.CharField', [], {'max_length': '100'}), + 'name': ('django.db.models.fields.CharField', [], {'max_length': '100'}) + }, + u'main.arch': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Arch', 'db_table': "'arches'"}, + 'agnostic': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'required_signoffs': ('django.db.models.fields.PositiveIntegerField', [], {'default': '2'}) + }, + u'main.donor': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Donor', 'db_table': "'donors'"}, + 'created': ('django.db.models.fields.DateTimeField', [], {}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'visible': ('django.db.models.fields.BooleanField', [], {'default': 'True'}) + }, + u'main.package': { + 'Meta': {'ordering': "('pkgname',)", 'unique_together': "(('pkgname', 'repo', 'arch'),)", 'object_name': 'Package', 'db_table': "'packages'"}, + 'arch': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'packages'", 'on_delete': 'models.PROTECT', 'to': u"orm['main.Arch']"}), + 'build_date': ('django.db.models.fields.DateTimeField', [], {'null': 'True'}), + 'compressed_size': ('main.fields.PositiveBigIntegerField', [], {}), + 'created': ('django.db.models.fields.DateTimeField', [], {}), + 'epoch': ('django.db.models.fields.PositiveIntegerField', [], {'default': '0'}), + 'filename': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'files_last_update': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}), + 'flag_date': ('django.db.models.fields.DateTimeField', [], {'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'installed_size': ('main.fields.PositiveBigIntegerField', [], {}), + 'last_update': ('django.db.models.fields.DateTimeField', [], {'db_index': 'True'}), + 'packager': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['auth.User']", 'null': 'True', 'on_delete': 'models.SET_NULL', 'blank': 'True'}), + 'packager_str': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pkgbase': ('django.db.models.fields.CharField', [], {'max_length': '255', 'db_index': 'True'}), + 'pkgdesc': ('django.db.models.fields.TextField', [], {'null': 'True'}), + 'pkgname': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pkgrel': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'pkgver': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'repo': ('django.db.models.fields.related.ForeignKey', [], {'related_name': "'packages'", 'on_delete': 'models.PROTECT', 'to': u"orm['main.Repo']"}), + 'signature_bytes': ('django.db.models.fields.BinaryField', [], {'null': 'True'}), + 'url': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True'}) + }, + u'main.packagefile': { + 'Meta': {'object_name': 'PackageFile', 'db_table': "'package_files'"}, + 'directory': ('django.db.models.fields.CharField', [], {'max_length': '255'}), + 'filename': ('django.db.models.fields.CharField', [], {'max_length': '255', 'null': 'True', 'blank': 'True'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'is_directory': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'pkg': ('django.db.models.fields.related.ForeignKey', [], {'to': u"orm['main.Package']"}) + }, + u'main.repo': { + 'Meta': {'ordering': "('name',)", 'object_name': 'Repo', 'db_table': "'repos'"}, + 'bugs_category': ('django.db.models.fields.SmallIntegerField', [], {'default': '2'}), + 'bugs_project': ('django.db.models.fields.SmallIntegerField', [], {'default': '1'}), + u'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}), + 'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '255'}), + 'staging': ('django.db.models.fields.BooleanField', [], {'default': 'False'}), + 'svn_root': ('django.db.models.fields.CharField', [], {'max_length': '64'}), + 'testing': ('django.db.models.fields.BooleanField', [], {'default': 'False'}) + } + } + + complete_apps = ['main'] diff --git a/main/models.py b/main/models.py index 70872c60..3f964082 100644 --- a/main/models.py +++ b/main/models.py @@ -108,7 +108,6 @@ class Package(models.Model): packager_str = models.CharField('packager string', max_length=255) packager = models.ForeignKey(User, null=True, blank=True, on_delete=models.SET_NULL) - pgp_signature = models.TextField('PGP signature', null=True, blank=True) signature_bytes = models.BinaryField('PGP signature', null=True) flag_date = models.DateTimeField(null=True, blank=True) -- cgit v1.2.3-54-g00ecf From e2fc5cfccdd2f844e75df75f44fff84f4181da7d Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Fri, 8 Nov 2013 13:14:27 -0600 Subject: Ensure user has a profile created when they go to edit it Use get_or_create, even though it leaves a bad taste in my mouth. The first user created won't have a profile becuase Django doesn't create one for users created at the command line, causing an exception when the user goes to edit it. Signed-off-by: Dan McGee --- devel/views.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/devel/views.py b/devel/views.py index 378d6d57..b6e85822 100644 --- a/devel/views.py +++ b/devel/views.py @@ -20,7 +20,7 @@ from django.utils.timezone import now from .forms import ProfileForm, UserProfileForm, NewUserForm -from .models import DeveloperKey +from .models import DeveloperKey, UserProfile from main.models import Package, PackageFile from main.models import Arch, Repo from news.models import News @@ -158,10 +158,11 @@ def clock(request): @login_required @never_cache def change_profile(request): + profile, _ = UserProfile.objects.get_or_create(user=request.user) if request.POST: form = ProfileForm(request.POST) profile_form = UserProfileForm(request.POST, request.FILES, - instance=request.user.userprofile) + instance=profile) if form.is_valid() and profile_form.is_valid(): request.user.email = form.cleaned_data['email'] if form.cleaned_data['passwd1']: @@ -172,7 +173,7 @@ def change_profile(request): return HttpResponseRedirect('/devel/') else: form = ProfileForm(initial={'email': request.user.email}) - profile_form = UserProfileForm(instance=request.user.userprofile) + profile_form = UserProfileForm(instance=profile) return render(request, 'devel/profile.html', {'form': form, 'profile_form': profile_form}) -- cgit v1.2.3-54-g00ecf From 833798f4fb7f629fdb8d7e57b5f25b31d395fa5e Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Mon, 11 Nov 2013 16:28:34 -0600 Subject: Filtered requiredby list for non-primary depends For something like gambas3 which has a makedepend on postgresql, we end up getting every single split package listed in the required by list for postgresql. This is a bit crazy and unnecessary, so slim it down a bit when possible by using a slightly crazy groupby function and some smarts in our get_requiredby function. Signed-off-by: Dan McGee --- main/models.py | 21 ++++++++++++++++++--- main/utils.py | 14 ++++++++++++++ 2 files changed, 32 insertions(+), 3 deletions(-) diff --git a/main/models.py b/main/models.py index 2ace0109..b3c3e409 100644 --- a/main/models.py +++ b/main/models.py @@ -9,7 +9,7 @@ from django.contrib.sites.models import Site from .fields import PositiveBigIntegerField -from .utils import set_created_field +from .utils import set_created_field, DependStandin from devel.models import DeveloperKey from packages.alpm import AlpmAPI @@ -247,6 +247,20 @@ def get_requiredby(self): if len(requiredby) == 0: return requiredby + # do we have duplicate pkgbase values for non-primary depends? + # if so, filter it down to base packages only + def grouper(depend): + p = depend.pkg + return (depend.deptype, p.pkgbase, p.repo.testing, p.repo.staging) + + filtered = [] + for (typ, pkgbase, _, _), dep_pkgs in groupby(requiredby, grouper): + dep_pkgs = list(dep_pkgs) + if typ == 'D' or len(dep_pkgs) == 1: + filtered.extend(dep_pkgs) + else: + filtered.append(DependStandin(dep_pkgs)) + # find another package by this name in a different testing or staging # repo; if we can't, we can short-circuit some checks repo_q = (Q(repo__testing=(not self.repo.testing)) | @@ -255,13 +269,13 @@ def get_requiredby(self): repo_q, pkgname=self.pkgname, arch=self.arch ).exclude(id=self.id).exists(): # there isn't one? short circuit, all required by entries are fine - return requiredby + return filtered trimmed = [] # for each unique package name, try to screen our package list down to # those packages in the same testing and staging category (yes or no) # iff there is a package in the same testing and staging category. - for _, dep_pkgs in groupby(requiredby, lambda x: x.pkg.pkgname): + for _, dep_pkgs in groupby(filtered, lambda x: x.pkg.pkgname): dep_pkgs = list(dep_pkgs) dep = dep_pkgs[0] if len(dep_pkgs) > 1: @@ -271,6 +285,7 @@ def get_requiredby(self): if len(dep_pkgs) > 0: dep = dep_pkgs[0] trimmed.append(dep) + return trimmed def get_depends(self): diff --git a/main/utils.py b/main/utils.py index 9ee8db58..97cc540a 100644 --- a/main/utils.py +++ b/main/utils.py @@ -187,4 +187,18 @@ def get_absolute_url(self): return '/packages/%s/%s/%s/' % ( self.repo.name.lower(), self.arch.name, self.pkgbase) + +class DependStandin(object): + '''Resembles a Depend object, and has a few of the same fields, but is + really a link to a base package rather than a single package.''' + def __init__(self, depends): + self._depends = depends + first = depends[0] + self.name = first.name + self.version = first.version + self.comparison = first.comparison + self.description = first.description + self.deptype = first.deptype + self.pkg = first.pkg.base_package() or PackageStandin(first.pkg) + # vim: set ts=4 sw=4 et: -- cgit v1.2.3-54-g00ecf From c1346ede6401ac19e6f669c81c2411794dcf81f3 Mon Sep 17 00:00:00 2001 From: Dan McGee Date: Mon, 11 Nov 2013 17:31:27 -0600 Subject: Add 2012 and 2013 retro sites From our friends over at web.archive.org again, thanks! Signed-off-by: Dan McGee --- retro/static/2012/CP_EN_BK_S_001.gif | Bin 0 -> 3036 bytes retro/static/2012/airvm_button.png | Bin 0 -> 4931 bytes retro/static/2012/archlogo.gif | Bin 0 -> 1845 bytes retro/static/2012/archlogo.png | Bin 0 -> 4192 bytes retro/static/2012/archnavbar.css | 33 + retro/static/2012/archweb-print.css | 24 + retro/static/2012/archweb.css | 1005 ++++++++++++++++++++ retro/static/2012/asc.gif | Bin 0 -> 54 bytes retro/static/2012/desc.gif | Bin 0 -> 54 bytes retro/static/2012/new.png | Bin 0 -> 378 bytes retro/static/2012/nosort.gif | Bin 0 -> 64 bytes retro/static/2012/rss.png | Bin 0 -> 725 bytes retro/static/2012/sevenl_button.png | Bin 0 -> 6840 bytes retro/static/2012/vnet_button.png | Bin 0 -> 4908 bytes retro/static/2013/airvm_button.png | Bin 0 -> 4931 bytes .../2013/apple-touch-icon-114x114.343cca8f850e.png | Bin 0 -> 2088 bytes .../2013/apple-touch-icon-144x144.38cf584757c3.png | Bin 0 -> 3063 bytes .../2013/apple-touch-icon-57x57.0cd0ab3349e2.png | Bin 0 -> 1173 bytes .../2013/apple-touch-icon-72x72.e502bac6368f.png | Bin 0 -> 1437 bytes retro/static/2013/archlogo.4fefb38dc270.png | Bin 0 -> 4192 bytes retro/static/2013/archweb.css | 1 + .../2013/bootstrap-typeahead.min.1aacd3d7f4db.js | 1 + retro/static/2013/click_and_pledge.png | Bin 0 -> 2284 bytes retro/static/2013/favicon.29302f683ff8.ico | Bin 0 -> 575 bytes retro/static/2013/jquery.js | 2 + retro/static/2013/konami.min.e165c814457d.js | 4 + retro/static/2013/rss.c5ebdc5318d6.png | 1 + retro/static/2013/rss.png | Bin 0 -> 707 bytes retro/static/2013/vector_tux.864e6cdcc23e.png | Bin 0 -> 165926 bytes retro/static/2013/vnet_button.png | Bin 0 -> 4908 bytes retro/templates/retro/index-2012-03-09.html | 485 ++++++++++ retro/templates/retro/index-2013-03-07.html | 482 ++++++++++ retro/views.py | 2 + 33 files changed, 2040 insertions(+) create mode 100644 retro/static/2012/CP_EN_BK_S_001.gif create mode 100644 retro/static/2012/airvm_button.png create mode 100644 retro/static/2012/archlogo.gif create mode 100644 retro/static/2012/archlogo.png create mode 100644 retro/static/2012/archnavbar.css create mode 100644 retro/static/2012/archweb-print.css create mode 100644 retro/static/2012/archweb.css create mode 100644 retro/static/2012/asc.gif create mode 100644 retro/static/2012/desc.gif create mode 100644 retro/static/2012/new.png create mode 100644 retro/static/2012/nosort.gif create mode 100644 retro/static/2012/rss.png create mode 100644 retro/static/2012/sevenl_button.png create mode 100644 retro/static/2012/vnet_button.png create mode 100644 retro/static/2013/airvm_button.png create mode 100644 retro/static/2013/apple-touch-icon-114x114.343cca8f850e.png create mode 100644 retro/static/2013/apple-touch-icon-144x144.38cf584757c3.png create mode 100644 retro/static/2013/apple-touch-icon-57x57.0cd0ab3349e2.png create mode 100644 retro/static/2013/apple-touch-icon-72x72.e502bac6368f.png create mode 100644 retro/static/2013/archlogo.4fefb38dc270.png create mode 100644 retro/static/2013/archweb.css create mode 100644 retro/static/2013/bootstrap-typeahead.min.1aacd3d7f4db.js create mode 100644 retro/static/2013/click_and_pledge.png create mode 100644 retro/static/2013/favicon.29302f683ff8.ico create mode 100644 retro/static/2013/jquery.js create mode 100644 retro/static/2013/konami.min.e165c814457d.js create mode 120000 retro/static/2013/rss.c5ebdc5318d6.png create mode 100644 retro/static/2013/rss.png create mode 100644 retro/static/2013/vector_tux.864e6cdcc23e.png create mode 100644 retro/static/2013/vnet_button.png create mode 100644 retro/templates/retro/index-2012-03-09.html create mode 100644 retro/templates/retro/index-2013-03-07.html diff --git a/retro/static/2012/CP_EN_BK_S_001.gif b/retro/static/2012/CP_EN_BK_S_001.gif new file mode 100644 index 00000000..41cf0885 Binary files /dev/null and b/retro/static/2012/CP_EN_BK_S_001.gif differ diff --git a/retro/static/2012/airvm_button.png b/retro/static/2012/airvm_button.png new file mode 100644 index 00000000..0acadc9c Binary files /dev/null and b/retro/static/2012/airvm_button.png differ diff --git a/retro/static/2012/archlogo.gif b/retro/static/2012/archlogo.gif new file mode 100644 index 00000000..e1852a06 Binary files /dev/null and b/retro/static/2012/archlogo.gif differ diff --git a/retro/static/2012/archlogo.png b/retro/static/2012/archlogo.png new file mode 100644 index 00000000..e873e94b Binary files /dev/null and b/retro/static/2012/archlogo.png differ diff --git a/retro/static/2012/archnavbar.css b/retro/static/2012/archnavbar.css new file mode 100644 index 00000000..d95832bc --- /dev/null +++ b/retro/static/2012/archnavbar.css @@ -0,0 +1,33 @@ +/* + * ARCH GLOBAL NAVBAR + * + * We're forcing all generic selectors with !important + * to help prevent other stylesheets from interfering. + * + */ + +/* container for the entire bar */ +#archnavbar { height: 40px !important; padding: 10px 15px !important; background: #333 !important; border-bottom: 5px #08c solid !important; } + +/* logo trickery -- GIF for IE6 and PNG for the rest */ +#archnavbarlogo { float: left !important; margin: 0 !important; padding: 0 !important; height: 40px !important; width: 190px !important; } +/* IE6 doesn't support alpha PNGs so we serve it a GIF */ +#archnavbarlogo { background: url('archlogo.gif') no-repeat !important; } +/* and use a proper PNG for all other modern browsers */ +html > body #archnavbarlogo { background: url('archlogo.png') no-repeat !important; } + +/* move the heading/paragraph text offscreen */ +#archnavbarlogo p { margin: 0 !important; padding: 0 !important; text-indent: -9999px !important; } +#archnavbarlogo h1 { margin: 0 !important; padding: 0 !important; text-indent: -9999px !important; } + +/* make the link the same size as the logo */ +#archnavbarlogo a { display: block !important; height: 40px !important; width: 190px !important; } + +/* display the list inline, float it to the right and style it */ +#archnavbar ul { display: inline !important; float: right !important; list-style: none !important; margin: 0 !important; padding: 0 !important; } +#archnavbar ul li { float: left !important; font-size: 14px !important; font-family: sans-serif !important; line-height: 45px !important; padding-right: 15px !important; padding-left: 15px !important; } + +/* style the links */ +#archnavbar ul#archnavbarlist li a { color: #999; font-weight: bold !important; text-decoration: none !important; } +#archnavbar ul li a:hover { color: white !important; text-decoration: underline !important; } + diff --git a/retro/static/2012/archweb-print.css b/retro/static/2012/archweb-print.css new file mode 100644 index 00000000..95c2a532 --- /dev/null +++ b/retro/static/2012/archweb-print.css @@ -0,0 +1,24 @@ + + + + + +/* + FILE ARCHIVED ON 16:45:26 Mar 12, 2012 AND RETRIEVED FROM THE + INTERNET ARCHIVE ON 22:32:15 Nov 11, 2013. + JAVASCRIPT APPENDED BY WAYBACK MACHINE, COPYRIGHT INTERNET ARCHIVE. + + ALL OTHER CONTENT MAY ALSO BE PROTECTED BY COPYRIGHT (17 U.S.C. + SECTION 108(a)(3)). +*/ +/* + * ARCH LINUX DJANGO (MAIN SITE) + * + * Stylesheet for printing + */ + +/* general styling */ +body { font: normal 100% sans-serif; } +#content { font-size: 0.812em; } +#archnavbarmenu, #archdev-navbar, .admin-actions { display: none; } + diff --git a/retro/static/2012/archweb.css b/retro/static/2012/archweb.css new file mode 100644 index 00000000..b96927b6 --- /dev/null +++ b/retro/static/2012/archweb.css @@ -0,0 +1,1005 @@ +/* + * ARCH LINUX DJANGO (MAIN SITE) + * + * Font sizing based on 16px browser defaults (use em): + * 14px = 0.875em + * 13px = 0.812em + * 12px = 0.75em + * 11px = 0.6875em + * + */ + +/* import the global navbar stylesheet */ +@import url('archnavbar.css'); + +/* simple reset */ +* { + margin: 0; + padding: 0; + line-height: 1.4; +} + +/* general styling */ +body { + min-width: 650px; + background: #f6f9fc; + color: #222; + font: normal 100% sans-serif; + text-align: center; +} + +p { + margin: .33em 0 1em; +} + +ol, +ul { + margin-bottom: 1em; + padding-left: 2em; +} + + ul { + list-style: square; + } + +code { + font: 1.2em monospace; + background: #ffd; + padding: 0.15em 0.25em; +} + +pre { + font: 1.2em monospace; + border: 1px solid #bdb; + background: #dfd; + padding: 0.5em; + margin: 1em; +} + + pre code { + display: block; + background: none; + } + +blockquote { + margin: 1.5em 2em; +} + +input { + vertical-align: middle; +} + +select[multiple] { + padding: 1px 0; +} + + select[multiple] option { + padding: 0 0.5em 0 0.3em; + } + +input[type=submit] { + padding: 0 0.6em; +} + +.clear { + clear: both; +} + +hr { + border: none; + border-top: 1px solid #888; +} + +img { + border: 0; +} + +/* scale fonts down to a sane default (16 * .812 = 13px) */ +#content { + font-size: 0.812em; +} + +/* link style */ +a { + text-decoration: none; +} + + a:link, + th a:visited { + color: #07b; + } + + a:visited { + color: #666; + } + + a:hover { + text-decoration: underline; + color: #666; + } + + a:active { + color: #e90; + } + +/* headings */ +h2 { + font-size: 1.5em; + margin-bottom: 0.5em; + border-bottom: 1px solid #888; +} + +h3 { + font-size: 1.25em; + margin-top: .5em; +} + +h4 { + font-size: 1.15em; + margin-top: 1em; +} + +h5 { + font-size: 1em; + margin-top: 1em; +} + +/* general layout */ +div#content { + width: 95%; + margin: 0 auto; + text-align: left; +} + +div#content-left-wrapper { + float: left; + width: 100%; /* req to keep content above sidebar in source code */ +} + +div#content-left { + margin: 0 340px 0 0; +} + +div#content-right { + float: left; + width: 300px; + margin-left: -300px; +} + +div.box { + margin-bottom: 1.5em; + padding: 0.65em; + background: #ecf2f5; + border: 1px solid #bcd; +} + +div#footer { + clear: both; + margin: 2em 0 1em; +} + + div#footer p { + margin: 0; + text-align: center; + font-size: 0.85em; + } + +/* alignment */ +div.center, +table.center, +img.center { + width: auto; + margin-left: auto; + margin-right: auto; +} + +p.center, +td.center, +th.center { + text-align: center; +} + +/* table generics */ +table { + width: 100%; + border-collapse: collapse; +} + + table .wrap { + white-space: normal; + } + +th, +td { + white-space: nowrap; + text-align: left; +} + + th { + vertical-align: middle; + font-weight: bold; + } + + td { + vertical-align: top; + } + +/* table pretty styles */ +table.pretty1 { + width: auto; + margin-top: 0.25em; + margin-bottom: 0.5em; + border-collapse: collapse; + border: 1px solid #bcd; +} + + table.pretty1 th { + padding: 0.35em; + background: #e4eeff; + border: 1px solid #bcd; + } + + table.pretty1 td { + padding: 0.35em; + border: 1px dotted #bcd; + } + +table.pretty2 { + width: auto; + margin-top: 0.25em; + margin-bottom: 0.5em; + border-collapse: collapse; + border: 1px solid #bbb; +} + + table.pretty2 th { + padding: 0.35em; + background: #eee; + border: 1px solid #bbb; + } + + table.pretty2 td { + padding: 0.35em; + border: 1px dotted #bbb; + } + +/* definition lists */ +dl { + clear: both; +} + + dl dt, + dl dd { + margin-bottom: 4px; + padding: 8px 0px 4px; + font-weight: bold; + border-top: 1px dotted #bbb; + } + + dl dt { + color: #333; + float:left; + padding-right:15px; + } + +/* forms and input styling */ +form p { + margin: 0.5em 0; +} + +fieldset { + border: 0; +} + +label { + width: 12em; + vertical-align: top; + display: inline-block; + font-weight: bold; +} + +input[type=text], +input[type=password], +textarea { + padding: 0.10em; +} + +form.general-form label, +form.general-form .form-help { + width: 10em; + vertical-align: top; + display: inline-block; +} + +form.general-form input[type=text], +form.general-form textarea { + width: 45%; +} + +/* archdev navbar */ +div#archdev-navbar { + margin: 1.5em 0; +} + + div#archdev-navbar ul { + list-style: none; + margin: -0.5em 0; + padding: 0; + } + + div#archdev-navbar li { + display: inline; + margin: 0; + padding: 0; + font-size: 0.9em; + } + + div#archdev-navbar li a { + padding: 0 0.5em; + color: #07b; + } + +/* error/info messages (x pkg is already flagged out-of-date, etc) */ +#sys-message { + width: 35em; + text-align: center; + margin: 1em auto; + padding: 0.5em; + background: #fff; + border: 1px solid #f00; +} + + #sys-message p { + margin: 0; + } + +ul.errorlist { + color: red; +} + +/** + * PAGE SPECIFIC STYLES + */ + +/* home: introduction */ +#intro p.readmore { + margin: -0.5em 0 0 0; + font-size: .9em; + text-align: right; +} + +/* home: news */ +#news { + margin-top: 1.5em; +} + + #news h3 { + float: left; + padding-bottom: .5em + } + + #news div { + margin-bottom: 1em; + } + + #news div p { + margin-bottom: 0.5em; + } + + #news .more { + font-weight: normal; + } + + #news .rss-icon { + float: right; + margin-top: 1em; + } + + #news h4 { + clear: both; + font-size: 1em; + margin-top: 1.5em; + border-bottom: 1px dotted #bbb; + } + + #news .timestamp { + float: right; + font-size: 0.85em; + margin: -1.8em 0.5em 0 0; + } + +/* home: arrowed headings */ +#news h3 a { + display: block; + background: #1794D1; + font-size: 15px; + padding: 2px 10px; + color: white; +} + + #news a:active { + color: white; + } + +h3 span.arrow { + display: block; + width: 0px; + height: 0px; + border-left: 6px solid transparent; + border-right: 6px solid transparent; + border-top: 6px solid #1794D1; + margin: 0 auto; + font-size: 0px; + line-height: 0px; +} + +/* home: pkgsearch box */ +#pkgsearch { + padding: 1em 0.75em; + background: #3ad; + color: #fff; + border: 1px solid #08b; +} + + #pkgsearch label { + width: auto; + padding: 0.1em 0; + } + + #pkgsearch input { + width: 10em; + float: right; + font-size: 1em; + color: #000; + background: #fff; + border: 1px solid #09c; + } + +/* home: recent pkg updates */ +#pkg-updates h3 { + margin: 0 0 0.3em; +} + + #pkg-updates .more { + font-weight: normal; + } + + #pkg-updates .rss-icon { + float: right; + margin: -2em 0 0 0; + } + + #pkg-updates table { + margin: 0; + } + + #pkg-updates td.pkg-name { + white-space: normal; + } + + #pkg-updates td.pkg-arch { + text-align: right; + } + + #pkg-updates span.testing { + font-style: italic; + } + + #pkg-updates span.staging { + font-style: italic; + color: #ff8040; + } + +/* home: sidebar navigation */ +div#nav-sidebar ul { + list-style: none; + margin: 0.5em 0 0.5em 1em; + padding: 0; +} + +/* home: sponsor banners */ +div#arch-sponsors img { + padding: 0.3em 0; +} + +/* home: sidebar components (navlist, sponsors, pkgsearch, etc) */ +div.widget { + margin-bottom: 1.5em; +} + +/* feeds page */ +#rss-feeds .rss { + padding-right: 20px; + background: url(rss.png) top right no-repeat; +} + +/* artwork: logo images */ +#artwork img.inverted { + background: #333; + padding: 0; +} + +#artwork div.imagelist img { + display: inline; + margin: 0.75em; +} + +/* news: article list */ +.news-nav { + float: right; + margin-top: -2.2em; +} + + .news-nav .prev, + .news-nav .next { + margin: 0 1em; + } + +/* news: article pages */ +div.news-article .article-info { + margin: 0; + color: #999; +} + +/* news: add/edit article */ +form#newsform { + width: 60em; +} + + form#newsform input[type=text], + form#newsform textarea { + width: 75%; + } + +/* donate: donor list */ +div#donor-list ul { + width: 100%; +} + /* max 4 columns, but possibly fewer if screen size doesn't allow for more */ + div#donor-list li { + float: left; + width: 25%; + min-width: 20em; + } + +/* download page */ +#arch-downloads h3 { + border-bottom: 1px dotted #bbb; +} + +table#download-torrents .cpu-arch { + text-align: center; +} + +table#download-mirrors { + width: auto; + margin-bottom: 1em; +} + + table#download-mirrors td.mirror-country { + padding-top: 1em; + } + + table#download-mirrors td.mirror-server { + padding-right: 1em; + } + + table#download-mirrors a { + display: block; + float: right; + width: 4em; + } + +/* pkglists/devlists */ +table.results { + font-size: 0.846em; + border-top: 1px dotted #999; + border-bottom: 1px dotted #999; +} + + table.results th { + padding: 0.5em 1em 0.25em 0.25em; + border-bottom: 1px solid #999; + white-space: nowrap; + background-color:#fff; + } + + /* additional styles for JS sorting */ + table.results th.header { + padding-right: 20px; + background-image: url(nosort.gif); + background-repeat: no-repeat; + background-position: center right; + cursor: pointer; + } + + table.results th.headerSortDown { + background-color: #e4eeff; + background-image: url(desc.gif); + } + + table.results th.headerSortUp { + background-color: #e4eeff; + background-image: url(asc.gif); + } + + table.results td { + padding: .3em 1em .3em 3px; + } + + table.results tr.odd { + background: #fff; + } + + table.results tr.even { + background: #e4eeff; + } + + table.results .flagged { + color: red; + } + +/* pkglist: layout */ +div#pkglist-about { + margin-top: 1.5em; +} + +/* pkglist: results navigation */ +#pkglist-stats-top, +#pkglist-stats-bottom { + font-size: 0.85em; +} + +#pkglist-results .pkglist-nav { + float: right; + margin-top: -2.2em; +} + +.pkglist-nav .prev { + margin-right: 1em; +} + +.pkglist-nav .next { + margin-right: 1em; +} + +/* search fields and other filter selections */ +.filter-criteria { + margin-bottom: 1em; +} + +.filter-criteria h3 { + font-size: 1em; + margin-top: 0; +} + +.filter-criteria div { + float: left; + margin-right: 1.65em; + font-size: 0.85em; +} + +.filter-criteria legend { + display: none; +} + +.filter-criteria label { + width: auto; + display: block; + font-weight: normal; +} + +/* pkgdetails: details links that float on the right */ +#pkgdetails #detailslinks { + float: right; +} + + #pkgdetails #detailslinks h4 { + margin-top: 0; + margin-bottom: 0.25em; + } + + #pkgdetails #detailslinks ul { + list-style: none; + padding: 0; + margin-bottom: 0; + font-size: 0.846em; + } + + #pkgdetails #detailslinks > div { + padding: 0.5em; + margin-bottom: 1em; + background: #eee; + border: 1px solid #bbb; + } + +#pkgdetails #actionlist .flagged { + color: red; + font-size: 0.9em; + font-style: italic; +} + +/* pkgdetails: pkg info */ +#pkgdetails #pkginfo { + width: auto; +} + + #pkgdetails #pkginfo td { + padding: 0.25em 0 0.25em 1.5em; + } + + #pkgdetails #pkginfo .userdata { + font-size: 0.85em; + padding: 0.5em; + } + +/* pkgdetails: flag package */ +form#flag-pkg-form label { + width: 10em; +} + +form#flag-pkg-form textarea, +form#flag-pkg-form input[type=text] { + width: 45%; +} + +/* pkgdetails: deps, required by and file lists */ +#pkgdetails #metadata { + clear: both; +} + +#pkgdetails #metadata h3 { + background: #555; + color: #fff; + font-size: 1em; + margin-bottom: 0.5em; + padding: 0.2em 0.35em; +} + +#pkgdetails #metadata ul { + list-style: none; + margin: 0; + padding: 0; +} + +#pkgdetails #metadata li { + padding-left: 0.5em; +} + +#pkgdetails #metadata p { + padding-left: 0.5em; +} + +#pkgdetails #metadata .message { + font-style: italic; +} + +#pkgdetails #metadata br { + clear: both; +} + +#pkgdetails #pkgdeps { + float: left; + width: 48%; + margin-right: 2%; +} + +#pkgdetails #metadata .virtual-dep, +#pkgdetails #metadata .testing-dep, +#pkgdetails #metadata .opt-dep, +#pkgdetails #metadata .dep-desc { + font-style: italic; +} +#pkgdetails #pkgreqs { + float: left; + width: 50%; +} + +#pkgdetails #pkgfiles { + clear: left; + padding-top: 1em; +} + +/* dev/TU biographies */ +div#arch-bio-toc { + width: 75%; + margin: 0 auto; + text-align: center; +} + + div#arch-bio-toc a { + white-space: nowrap; + } + +table.arch-bio-entry td.pic { + vertical-align: top; + padding-right: 15px; + padding-top: 10px; +} + + table.arch-bio-entry td.pic img { + padding: 4px; + border: 1px solid #ccc; + } + +table.arch-bio-entry table.bio { + margin-bottom: 2em; +} + + table.arch-bio-entry table.bio th { + text-align: left; + padding-right: 0.5em; + vertical-align: top; + white-space: nowrap; + } + + table.arch-bio-entry table.bio td { + width: 100%; + padding-bottom: 0.25em; + } + +/* dev: login/out */ +table#dev-login { + width: auto; +} + +/* dev dashboard: flagged packages */ +form#dash-pkg-notify { + text-align: right; + padding: 1em 0 0; + margin-top: 1em; + font-size: 0.85em; + border-top: 1px dotted #bbb; +} + + form#dash-pkg-notify label { + width: auto; + font-weight: normal; + } + + form#dash-pkg-notify input { + vertical-align: middle; + margin: 0 0.25em; + } + + form#dash-pkg-notify input[type=submit] { + margin-top: -0.25em; + } + + form#dash-pkg-notify p { + margin: 0; + } + +table.dash-stats .key { + width: 50%; +} + +/* dev dashboard: admin actions (add news items, todo list, etc) */ +ul.admin-actions { + float: right; + list-style: none; + margin-top: -2.5em; +} + + ul.admin-actions li { + display: inline; + padding-left: 1.5em; + } + +/* todo lists (public and private) */ +.todo-table .complete { + color: green; +} + +.todo-table .incomplete { + color: red; +} +.todo-info { + margin: 0; color: #999; +} + +.todo-list h4 { + margin-top: 0; + margin-bottom: 0.4em; +} + +/* dev: signoff page */ +#dev-signoffs tr:hover { + background: #ffd; +} + +ul.signoff-list { + list-style: none; + margin: 0; + padding: 0; +} + +.signoff-yes { + color: green; + font-weight: bold; +} + +.signoff-no { + color: red; +} + +.signoff-bad { + color: darkorange; +} + +.signoff-disabled { + color: gray; +} + +/* iso testing feedback form */ +#releng-feedback label { + width: auto; + display: inline; + font-weight: normal; +} + +#releng-feedback ul { + padding-left: 1em; +} + +#releng-feedback li { + list-style: none; +} + +#releng-feedback ul+.helptext { + position: relative; top: -0.9em; +} + +#releng-result .success-yes { + color: green; +} + +#releng-result .success-no { + color: red; +} + +/* highlight current website in the navbar */ +#archnavbar.anb-home ul li#anb-home a, +#archnavbar.anb-packages ul li#anb-packages a, +#archnavbar.anb-download ul li#anb-download a { + color: white !important; +} + +/* visualizations page */ +.visualize-buttons { + margin: 0.5em 0.33em; +} + + .visualize-buttons button.active { + depressed: true; + } + +.visualize-chart { + position: relative; + height: 500px; + margin: 0.33em; +} + +#visualize-archrepo .treemap-cell { + border: solid 1px white; + overflow: hidden; + position: absolute; +} + + #visualize-archrepo .treemap-cell span { + padding: 3px; + font-size: 0.85em; + line-height: 1em; + } + +#visualize-keys svg { + width: 100%; +} + + #visualize-keys circle { + stroke-width: 1.5px; + } + + #visualize-keys line { + stroke: #888; + } diff --git a/retro/static/2012/asc.gif b/retro/static/2012/asc.gif new file mode 100644 index 00000000..74157867 Binary files /dev/null and b/retro/static/2012/asc.gif differ diff --git a/retro/static/2012/desc.gif b/retro/static/2012/desc.gif new file mode 100644 index 00000000..3b30b3c5 Binary files /dev/null and b/retro/static/2012/desc.gif differ diff --git a/retro/static/2012/new.png b/retro/static/2012/new.png new file mode 100644 index 00000000..6a9bf037 Binary files /dev/null and b/retro/static/2012/new.png differ diff --git a/retro/static/2012/nosort.gif b/retro/static/2012/nosort.gif new file mode 100644 index 00000000..fac668fc Binary files /dev/null and b/retro/static/2012/nosort.gif differ diff --git a/retro/static/2012/rss.png b/retro/static/2012/rss.png new file mode 100644 index 00000000..c9164592 Binary files /dev/null and b/retro/static/2012/rss.png differ diff --git a/retro/static/2012/sevenl_button.png b/retro/static/2012/sevenl_button.png new file mode 100644 index 00000000..93adcdf0 Binary files /dev/null and b/retro/static/2012/sevenl_button.png differ diff --git a/retro/static/2012/vnet_button.png b/retro/static/2012/vnet_button.png new file mode 100644 index 00000000..22cfa9e4 Binary files /dev/null and b/retro/static/2012/vnet_button.png differ diff --git a/retro/static/2013/airvm_button.png b/retro/static/2013/airvm_button.png new file mode 100644 index 00000000..0acadc9c Binary files /dev/null and b/retro/static/2013/airvm_button.png differ diff --git a/retro/static/2013/apple-touch-icon-114x114.343cca8f850e.png b/retro/static/2013/apple-touch-icon-114x114.343cca8f850e.png new file mode 100644 index 00000000..a5b4282a Binary files /dev/null and b/retro/static/2013/apple-touch-icon-114x114.343cca8f850e.png differ diff --git a/retro/static/2013/apple-touch-icon-144x144.38cf584757c3.png b/retro/static/2013/apple-touch-icon-144x144.38cf584757c3.png new file mode 100644 index 00000000..cd177f2c Binary files /dev/null and b/retro/static/2013/apple-touch-icon-144x144.38cf584757c3.png differ diff --git a/retro/static/2013/apple-touch-icon-57x57.0cd0ab3349e2.png b/retro/static/2013/apple-touch-icon-57x57.0cd0ab3349e2.png new file mode 100644 index 00000000..d7d592c7 Binary files /dev/null and b/retro/static/2013/apple-touch-icon-57x57.0cd0ab3349e2.png differ diff --git a/retro/static/2013/apple-touch-icon-72x72.e502bac6368f.png b/retro/static/2013/apple-touch-icon-72x72.e502bac6368f.png new file mode 100644 index 00000000..5983885f Binary files /dev/null and b/retro/static/2013/apple-touch-icon-72x72.e502bac6368f.png differ diff --git a/retro/static/2013/archlogo.4fefb38dc270.png b/retro/static/2013/archlogo.4fefb38dc270.png new file mode 100644 index 00000000..e873e94b Binary files /dev/null and b/retro/static/2013/archlogo.4fefb38dc270.png differ diff --git a/retro/static/2013/archweb.css b/retro/static/2013/archweb.css new file mode 100644 index 00000000..22c30e76 --- /dev/null +++ b/retro/static/2013/archweb.css @@ -0,0 +1 @@ +#archnavbar{height:40px!important;padding:10px 15px!important;background:#333!important;border-bottom:5px #08c solid!important}#archnavbarlogo{float:left!important;margin:0!important;padding:0!important;height:40px!important;width:190px!important;background:url(archlogo.4fefb38dc270.png) no-repeat!important}#archnavbarlogo h1{margin:0!important;padding:0!important;text-indent:-9999px!important}#archnavbarlogo a{display:block!important;height:40px!important;width:190px!important}#archnavbarlist{display:inline!important;float:right!important;list-style:none!important;margin:0!important;padding:0!important}#archnavbarlist li{float:left!important;font-size:14px!important;font-family:sans-serif!important;line-height:45px!important;padding-right:15px!important;padding-left:15px!important}#archnavbarlist li a{color:#999;font-weight:bold!important;text-decoration:none!important}#archnavbarlist li a:hover{color:white!important;text-decoration:underline!important}*{margin:0;padding:0;line-height:1.4}body{min-width:650px;background:#f6f9fc;color:#222;font:normal 100% sans-serif;text-align:center}p{margin:.33em 0 1em}ol,ul{margin-bottom:1em;padding-left:2em}ul{list-style:square}code{font:1.2em monospace;background:#ffd;padding:.15em .25em}pre{font:1.2em monospace;border:1px solid #bdb;background:#dfd;padding:.5em;margin:1em}pre code{display:block;background:none}blockquote{margin:1.5em 2em}input{vertical-align:middle}select[multiple]{padding:1px 0}select[multiple] option{padding:0 .5em 0 .3em}input[type=submit]{padding:0 .6em}.clear{clear:both}.hide{display:none}hr{border:none;border-top:1px solid #888}img{border:0}#content{font-size:.812em}a{text-decoration:none}a:link,th a:visited{color:#07b}a:visited{color:#666}a:hover{text-decoration:underline;color:#666}a:active{color:#e90}a.headerlink{visibility:hidden;padding-left:.5em}h3:hover>a.headerlink{visibility:visible}h2{font-size:1.5em;margin-bottom:.5em;border-bottom:1px solid #888}h3{font-size:1.25em;margin-top:.5em}h4{font-size:1.15em;margin-top:1em}h5{font-size:1em;margin-top:1em}#content{width:95%;margin:0 auto;text-align:left}#content-left-wrapper{float:left;width:100%}#content-left{margin:0 340px 0 0}#content-right{float:left;width:300px;margin-left:-300px}div.box{margin-bottom:1.5em;padding:.65em;background:#ecf2f5;border:1px solid #bcd}#footer{clear:both;margin:2em 0 1em}#footer p{margin:0;text-align:center;font-size:.85em}div.center,table.center,img.center{width:auto;margin-left:auto;margin-right:auto}p.center,td.center,th.center{text-align:center}table{width:100%;border-collapse:collapse}table .wrap{white-space:normal}th,td{white-space:nowrap;text-align:left}th{vertical-align:middle;font-weight:bold}td{vertical-align:top}table.pretty1{width:auto;margin-top:.25em;margin-bottom:.5em;border-collapse:collapse;border:1px solid #bcd}.pretty1 th{padding:.35em;background:#e4eeff;border:1px solid #bcd}.pretty1 td{padding:.35em;border:1px dotted #bcd}table.pretty2{width:auto;margin-top:.25em;margin-bottom:.5em;border-collapse:collapse;border:1px solid #bbb}.pretty2 th{padding:.35em;background:#eee;border:1px solid #bbb}.pretty2 td{padding:.35em;border:1px dotted #bbb}table.compact{width:auto}.compact td{padding:.25em 0 .25em 1.5em}dl{clear:both}dl dt,dl dd{margin-bottom:4px;padding:8px 0 4px;font-weight:bold;border-top:1px dotted #bbb}dl dt{color:#333;float:left;padding-right:15px}form p{margin:.5em 0}fieldset{border:0}label{width:12em;vertical-align:top;display:inline-block;font-weight:bold}input[type=text],input[type=password],textarea{padding:.10em}form.general-form label,form.general-form .form-help{width:10em;vertical-align:top;display:inline-block}form.general-form input[type=text],form.general-form textarea{width:45%}#archdev-navbar{margin:1.5em 0}#archdev-navbar ul{list-style:none;margin:-0.5em 0;padding:0}#archdev-navbar li{display:inline;margin:0;padding:0;font-size:.9em}#archdev-navbar li a{padding:0 .5em;color:#07b}#sys-message{width:35em;text-align:center;margin:1em auto;padding:.5em;background:#fff;border:1px solid #f00}#sys-message p{margin:0}ul.errorlist{color:red}table th.tablesorter-header{padding-right:20px;background-image:url(data:image/gif;base64,R0lGODlhFQAJAIAAACMtMP///yH5BAEAAAEALAAAAAAVAAkAAAIXjI+AywnaYnhUMoqt3gZXPmVg94yJVQAAOw==);background-repeat:no-repeat;background-position:center right;cursor:pointer}table thead th.tablesorter-headerAsc{background-color:#e4eeff;background-image:url(data:image/gif;base64,R0lGODlhFQAEAIAAACMtMP///yH5BAEAAAEALAAAAAAVAAQAAAINjI8Bya2wnINUMopZAQA7)}table thead th.tablesorter-headerDesc{background-color:#e4eeff;background-image:url(data:image/gif;base64,R0lGODlhFQAEAIAAACMtMP///yH5BAEAAAEALAAAAAAVAAQAAAINjB+gC+jP2ptn0WskLQA7)}table thead th.sorter-false{background-image:url("");cursor:default}#intro p.readmore{margin:-0.5em 0 0 0;font-size:.9em;text-align:right}#news{margin-top:1.5em}#news h3{float:left;padding-bottom:.5em}#news div{margin-bottom:1em}#news div p{margin-bottom:.5em}#news .more{font-weight:normal}#news .rss-icon{float:right;margin-top:1em}#news h4{clear:both;font-size:1em;margin-top:1.5em;border-bottom:1px dotted #bbb}#news .timestamp{float:right;font-size:.85em;margin:-1.8em .5em 0 0}#news h3 a{display:block;background:#1794D1;font-size:15px;padding:2px 10px;color:white}#news a:active{color:white}h3 span.arrow{display:block;width:0;height:0;border-left:6px solid transparent;border-right:6px solid transparent;border-top:6px solid #1794D1;margin:0 auto;font-size:0;line-height:0}#pkgsearch{padding:1em .75em;background:#3ad;color:#fff;border:1px solid #08b}#pkgsearch label{width:auto;padding:.1em 0}#pkgsearch input{width:10em;float:right;font-size:1em;color:#000;background:#fff;border:1px solid #09c}.pkgsearch-typeahead{position:absolute;top:100%;left:0;z-index:1000;display:none;float:left;padding:.15em .1em;margin:0;min-width:10em;font-size:.812em;text-align:left;list-style:none;background-color:#f6f9fc;border:1px solid #09c}.pkgsearch-typeahead li a{color:#000}.pkgsearch-typeahead li.active a{color:#07b}#pkg-updates h3{margin:0 0 .3em}#pkg-updates .more{font-weight:normal}#pkg-updates .rss-icon{float:right;margin:-2em 0 0 0}#pkg-updates table{margin:0}#pkg-updates td.pkg-name{white-space:normal}#pkg-updates td.pkg-arch{text-align:right}#pkg-updates span.testing{font-style:italic}#pkg-updates span.staging{font-style:italic;color:#ff8040}#nav-sidebar ul{list-style:none;margin:.5em 0 .5em 1em;padding:0}#arch-sponsors img{padding:.3em 0}div.widget{margin-bottom:1.5em}#konami{position:fixed;top:0;left:0;width:100%;height:100%;text-align:center;opacity:.6}#rss-feeds .rss{padding-right:20px;background:url(rss.c5ebdc5318d6.png) top right no-repeat}#artwork img.inverted{background:#333;padding:0}#artwork div.imagelist img{display:inline;margin:.75em}.news-nav{float:right;margin-top:-2.2em}.news-nav .prev,.news-nav .next{margin:0 1em}div.news-article .article-info{margin:0;color:#999}#newsform{width:60em}#newsform input[type=text],#newsform textarea{width:75%}#donor-list ul{width:100%}#donor-list li{float:left;width:25%;min-width:20em}#arch-downloads h3{border-bottom:1px dotted #bbb}table.results{font-size:.846em;border-top:1px dotted #999;border-bottom:1px dotted #999}.results th{padding:.5em 1em .25em .25em;border-bottom:1px solid #999;white-space:nowrap;background-color:#fff}.results td{padding:.3em 1em .3em 3px}.results tr.odd{background:#fff}.results tr.even{background:#e4eeff}.results .flagged{color:red}#pkglist-about{margin-top:1.5em}.pkglist-stats{font-size:.85em}#pkglist-results .pkglist-nav{float:right;margin-top:-2.2em}.pkglist-nav .prev{margin-right:1em}.pkglist-nav .next{margin-right:1em}.filter-criteria{margin-bottom:1em}.filter-criteria h3{font-size:1em;margin-top:0}.filter-criteria div{float:left;margin-right:1.65em;font-size:.85em}.filter-criteria legend{display:none}.filter-criteria label{width:auto;display:block;font-weight:normal}#pkgdetails #detailslinks{float:right}#pkgdetails #detailslinks h4{margin-top:0;margin-bottom:.25em}#pkgdetails #detailslinks ul{list-style:none;padding:0;margin-bottom:0;font-size:.846em}#pkgdetails #detailslinks>div{padding:.5em;margin-bottom:1em;background:#eee;border:1px solid #bbb}#pkgdetails #actionlist .flagged{color:red;font-size:.9em;font-style:italic}#pkgdetails #pkginfo{width:auto}#pkgdetails #pkginfo td{padding:.25em 0 .25em 1.5em}#pkgdetails #pkginfo .userdata{font-size:.85em;padding:.5em}#flag-pkg-form label{width:10em}#flag-pkg-form textarea,#flag-pkg-form input[type=text]{width:45%}#pkgdetails #metadata{clear:both}#pkgdetails #metadata h3{background:#555;color:#fff;font-size:1em;margin-bottom:.5em;padding:.2em .35em}#pkgdetails #metadata ul{list-style:none;margin:0;padding:0}#pkgdetails #metadata li{padding-left:.5em}#pkgdetails #metadata p{padding-left:.5em}#pkgdetails #metadata .message{font-style:italic}#pkgdetails #metadata br{clear:both}#pkgdetails #pkgdeps{float:left;width:48%;margin-right:2%}#pkgdetails #metadata .virtual-dep,#pkgdetails #metadata .testing-dep,#pkgdetails #metadata .staging-dep,#pkgdetails #metadata .opt-dep,#pkgdetails #metadata .make-dep,#pkgdetails #metadata .check-dep,#pkgdetails #metadata .dep-desc{font-style:italic}#pkgdetails #pkgreqs{float:left;width:50%}#pkgdetails #pkgfiles{clear:left;padding-top:1em}#pkgfilelist li.d{color:#666}#pkgfilelist li.f{}table td.country{white-space:normal}#list-generator div ul{list-style:none;display:inline;padding-left:0}#list-generator div ul li{display:inline}#visualize-mirror .axis path,#visualize-mirror .axis line{fill:none;stroke:#000;stroke-width:3px;shape-rendering:crispEdges}#visualize-mirror .url-dot{stroke:#000}#visualize-mirror .url-line{fill:none;stroke-width:1.5px}#arch-bio-toc{width:75%;margin:0 auto;text-align:center}#arch-bio-toc a{white-space:nowrap}.arch-bio-entry{width:75%;min-width:640px;margin:0 auto}.arch-bio-entry td.pic{vertical-align:top;padding-right:15px;padding-top:2.25em}.arch-bio-entry td.pic img{padding:4px;border:1px solid #ccc}.arch-bio-entry td h3{border-bottom:1px dotted #ccc;margin-bottom:.5em}.arch-bio-entry table.bio{margin-bottom:2em}.arch-bio-entry table.bio th{color:#666;font-weight:normal;text-align:right;padding-right:.5em;vertical-align:top;white-space:nowrap}.arch-bio-entry table.bio td{width:100%;padding-bottom:.25em;white-space:normal}#dev-login{width:auto}#dash-pkg-notify{text-align:right;padding:1em 0 0;margin-top:1em;font-size:.85em;border-top:1px dotted #bbb}#dash-pkg-notify label{width:auto;font-weight:normal}#dash-pkg-notify input{vertical-align:middle;margin:0 .25em}#dash-pkg-notify input[type=submit]{margin-top:-0.25em}#dash-pkg-notify p{margin:0}table.dash-stats .key{width:50%}ul.admin-actions{float:right;list-style:none;margin-top:-2.5em}ul.admin-actions li{display:inline;padding-left:1.5em}.todo-table .complete,.signoff-yes,#key-status .signed-yes,#releng-result .success-yes,#release-list .available-yes{color:green}.todo-table .incomplete,.signoff-no,#key-status .signed-no,#releng-result .success-no,#release-list .available-no{color:red}.todo-table .inprogress,.signoff-bad{color:darkorange}.todo-info{margin:0;color:#999}.todo-list h4{margin-top:0;margin-bottom:.4em}#dev-signoffs tr:hover{background:#ffd}ul.signoff-list{list-style:none;margin:0;padding:0}.signoff-yes{font-weight:bold}.signoff-disabled{color:gray}#releng-feedback label{width:auto;display:inline;font-weight:normal}#releng-feedback ul{padding-left:1em}#releng-feedback li{list-style:none}#releng-feedback ul+.helptext{position:relative;top:-0.9em}#archnavbar.anb-home ul li#anb-home a,#archnavbar.anb-packages ul li#anb-packages a,#archnavbar.anb-download ul li#anb-download a{color:white!important}.visualize-buttons{margin:.5em .33em}.visualize-buttons button.active{depressed:true}.visualize-chart{position:relative;height:500px;margin:.33em}#visualize-archrepo .treemap-cell{border:solid 1px white;overflow:hidden;position:absolute}#visualize-archrepo .treemap-cell span{padding:3px;font-size:.85em;line-height:1em}#visualize-keys svg{width:100%;height:100%} diff --git a/retro/static/2013/bootstrap-typeahead.min.1aacd3d7f4db.js b/retro/static/2013/bootstrap-typeahead.min.1aacd3d7f4db.js new file mode 100644 index 00000000..7d555ed9 --- /dev/null +++ b/retro/static/2013/bootstrap-typeahead.min.1aacd3d7f4db.js @@ -0,0 +1 @@ +!function(e){"use strict";var t=function(t,n){this.$element=e(t),this.options=e.extend({},e.fn.typeahead.defaults,n),this.matcher=this.options.matcher||this.matcher,this.sorter=this.options.sorter||this.sorter,this.highlighter=this.options.highlighter||this.highlighter,this.updater=this.options.updater||this.updater,this.$menu=e(this.options.menu).appendTo("body"),this.source=this.options.source,this.shown=!1,this.listen()};t.prototype={constructor:t,select:function(){var e=this.$menu.find(".active").attr("data-value");return e&&this.$element.val(this.updater(e)).change(),this.hide()},updater:function(e){return e},show:function(){var t=e.extend({},this.$element.offset(),{height:this.$element[0].offsetHeight});return this.$menu.css({top:t.top+t.height,left:t.left}),this.$menu.show(),this.shown=!0,this},hide:function(){return this.$menu.hide(),this.shown=!1,this},lookup:function(t){var n;return this.query=this.$element.val(),!this.query||this.query.length"+t+""})},render:function(t){var n=this;return t=e(t).map(function(t,r){return t=e(n.options.item).attr("data-value",r),t.find("a").html(n.highlighter(r)),t[0]}),this.$menu.html(t),this},next:function(t){var n=this.$menu.find(".active").removeClass("active"),r=n.next();r.length||(r=e(this.$menu.find("li")[0])),r.addClass("active")},prev:function(e){var t=this.$menu.find(".active").removeClass("active"),n=t.prev();n.length||(n=this.$menu.find("li").last()),n.addClass("active")},listen:function(){this.$element.on("blur",e.proxy(this.blur,this)).on("keypress",e.proxy(this.keypress,this)).on("keyup",e.proxy(this.keyup,this)),(e.browser.chrome||e.browser.webkit||e.browser.msie)&&this.$element.on("keydown",e.proxy(this.keydown,this)),this.$menu.on("click",e.proxy(this.click,this)).on("mouseenter","li",e.proxy(this.mouseenter,this))},move:function(e){if(!this.shown)return;switch(e.keyCode){case 9:case 13:case 27:e.preventDefault();break;case 38:e.preventDefault(),this.prev();break;case 40:e.preventDefault(),this.next()}e.stopPropagation()},keydown:function(t){this.suppressKeyPressRepeat=!~e.inArray(t.keyCode,[40,38,9,13,27]),this.move(t)},keypress:function(e){if(this.suppressKeyPressRepeat)return;this.move(e)},keyup:function(e){switch(e.keyCode){case 40:case 38:break;case 9:case 13:if(!this.shown)return;this.select();break;case 27:if(!this.shown)return;this.hide();break;default:this.lookup()}e.stopPropagation(),e.preventDefault()},blur:function(e){var t=this;setTimeout(function(){t.hide()},150)},click:function(e){e.stopPropagation(),e.preventDefault(),this.select()},mouseenter:function(t){this.$menu.find(".active").removeClass("active"),e(t.currentTarget).addClass("active")}},e.fn.typeahead=function(n){return this.each(function(){var r=e(this),i=r.data("typeahead"),s=typeof n=="object"&&n;i||r.data("typeahead",i=new t(this,s)),typeof n=="string"&&i[n]()})},e.fn.typeahead.defaults={source:[],items:8,menu:'',item:'
  • ',minLength:1},e.fn.typeahead.Constructor=t,e(function(){e("body").on("focus.typeahead.data-api",'[data-provide="typeahead"]',function(t){var n=e(this);if(n.data("typeahead"))return;t.preventDefault(),n.typeahead(n.data())})})}(window.jQuery) \ No newline at end of file diff --git a/retro/static/2013/click_and_pledge.png b/retro/static/2013/click_and_pledge.png new file mode 100644 index 00000000..078bf88e Binary files /dev/null and b/retro/static/2013/click_and_pledge.png differ diff --git a/retro/static/2013/favicon.29302f683ff8.ico b/retro/static/2013/favicon.29302f683ff8.ico new file mode 100644 index 00000000..55497b85 Binary files /dev/null and b/retro/static/2013/favicon.29302f683ff8.ico differ diff --git a/retro/static/2013/jquery.js b/retro/static/2013/jquery.js new file mode 100644 index 00000000..83589daa --- /dev/null +++ b/retro/static/2013/jquery.js @@ -0,0 +1,2 @@ +/*! jQuery v1.8.3 jquery.com | jquery.org/license */ +(function(e,t){function _(e){var t=M[e]={};return v.each(e.split(y),function(e,n){t[n]=!0}),t}function H(e,n,r){if(r===t&&e.nodeType===1){var i="data-"+n.replace(P,"-$1").toLowerCase();r=e.getAttribute(i);if(typeof r=="string"){try{r=r==="true"?!0:r==="false"?!1:r==="null"?null:+r+""===r?+r:D.test(r)?v.parseJSON(r):r}catch(s){}v.data(e,n,r)}else r=t}return r}function B(e){var t;for(t in e){if(t==="data"&&v.isEmptyObject(e[t]))continue;if(t!=="toJSON")return!1}return!0}function et(){return!1}function tt(){return!0}function ut(e){return!e||!e.parentNode||e.parentNode.nodeType===11}function at(e,t){do e=e[t];while(e&&e.nodeType!==1);return e}function ft(e,t,n){t=t||0;if(v.isFunction(t))return v.grep(e,function(e,r){var i=!!t.call(e,r,e);return i===n});if(t.nodeType)return v.grep(e,function(e,r){return e===t===n});if(typeof t=="string"){var r=v.grep(e,function(e){return e.nodeType===1});if(it.test(t))return v.filter(t,r,!n);t=v.filter(t,r)}return v.grep(e,function(e,r){return v.inArray(e,t)>=0===n})}function lt(e){var t=ct.split("|"),n=e.createDocumentFragment();if(n.createElement)while(t.length)n.createElement(t.pop());return n}function Lt(e,t){return e.getElementsByTagName(t)[0]||e.appendChild(e.ownerDocument.createElement(t))}function At(e,t){if(t.nodeType!==1||!v.hasData(e))return;var n,r,i,s=v._data(e),o=v._data(t,s),u=s.events;if(u){delete o.handle,o.events={};for(n in u)for(r=0,i=u[n].length;r").appendTo(i.body),n=t.css("display");t.remove();if(n==="none"||n===""){Pt=i.body.appendChild(Pt||v.extend(i.createElement("iframe"),{frameBorder:0,width:0,height:0}));if(!Ht||!Pt.createElement)Ht=(Pt.contentWindow||Pt.contentDocument).document,Ht.write(""),Ht.close();t=Ht.body.appendChild(Ht.createElement(e)),n=Dt(t,"display"),i.body.removeChild(Pt)}return Wt[e]=n,n}function fn(e,t,n,r){var i;if(v.isArray(t))v.each(t,function(t,i){n||sn.test(e)?r(e,i):fn(e+"["+(typeof i=="object"?t:"")+"]",i,n,r)});else if(!n&&v.type(t)==="object")for(i in t)fn(e+"["+i+"]",t[i],n,r);else r(e,t)}function Cn(e){return function(t,n){typeof t!="string"&&(n=t,t="*");var r,i,s,o=t.toLowerCase().split(y),u=0,a=o.length;if(v.isFunction(n))for(;u)[^>]*$|#([\w\-]*)$)/,E=/^<(\w+)\s*\/?>(?:<\/\1>|)$/,S=/^[\],:{}\s]*$/,x=/(?:^|:|,)(?:\s*\[)+/g,T=/\\(?:["\\\/bfnrt]|u[\da-fA-F]{4})/g,N=/"[^"\\\r\n]*"|true|false|null|-?(?:\d\d*\.|)\d+(?:[eE][\-+]?\d+|)/g,C=/^-ms-/,k=/-([\da-z])/gi,L=function(e,t){return(t+"").toUpperCase()},A=function(){i.addEventListener?(i.removeEventListener("DOMContentLoaded",A,!1),v.ready()):i.readyState==="complete"&&(i.detachEvent("onreadystatechange",A),v.ready())},O={};v.fn=v.prototype={constructor:v,init:function(e,n,r){var s,o,u,a;if(!e)return this;if(e.nodeType)return this.context=this[0]=e,this.length=1,this;if(typeof e=="string"){e.charAt(0)==="<"&&e.charAt(e.length-1)===">"&&e.length>=3?s=[null,e,null]:s=w.exec(e);if(s&&(s[1]||!n)){if(s[1])return n=n instanceof v?n[0]:n,a=n&&n.nodeType?n.ownerDocument||n:i,e=v.parseHTML(s[1],a,!0),E.test(s[1])&&v.isPlainObject(n)&&this.attr.call(e,n,!0),v.merge(this,e);o=i.getElementById(s[2]);if(o&&o.parentNode){if(o.id!==s[2])return r.find(e);this.length=1,this[0]=o}return this.context=i,this.selector=e,this}return!n||n.jquery?(n||r).find(e):this.constructor(n).find(e)}return v.isFunction(e)?r.ready(e):(e.selector!==t&&(this.selector=e.selector,this.context=e.context),v.makeArray(e,this))},selector:"",jquery:"1.8.3",length:0,size:function(){return this.length},toArray:function(){return l.call(this)},get:function(e){return e==null?this.toArray():e<0?this[this.length+e]:this[e]},pushStack:function(e,t,n){var r=v.merge(this.constructor(),e);return r.prevObject=this,r.context=this.context,t==="find"?r.selector=this.selector+(this.selector?" ":"")+n:t&&(r.selector=this.selector+"."+t+"("+n+")"),r},each:function(e,t){return v.each(this,e,t)},ready:function(e){return v.ready.promise().done(e),this},eq:function(e){return e=+e,e===-1?this.slice(e):this.slice(e,e+1)},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},slice:function(){return this.pushStack(l.apply(this,arguments),"slice",l.call(arguments).join(","))},map:function(e){return this.pushStack(v.map(this,function(t,n){return e.call(t,n,t)}))},end:function(){return this.prevObject||this.constructor(null)},push:f,sort:[].sort,splice:[].splice},v.fn.init.prototype=v.fn,v.extend=v.fn.extend=function(){var e,n,r,i,s,o,u=arguments[0]||{},a=1,f=arguments.length,l=!1;typeof u=="boolean"&&(l=u,u=arguments[1]||{},a=2),typeof u!="object"&&!v.isFunction(u)&&(u={}),f===a&&(u=this,--a);for(;a0)return;r.resolveWith(i,[v]),v.fn.trigger&&v(i).trigger("ready").off("ready")},isFunction:function(e){return v.type(e)==="function"},isArray:Array.isArray||function(e){return v.type(e)==="array"},isWindow:function(e){return e!=null&&e==e.window},isNumeric:function(e){return!isNaN(parseFloat(e))&&isFinite(e)},type:function(e){return e==null?String(e):O[h.call(e)]||"object"},isPlainObject:function(e){if(!e||v.type(e)!=="object"||e.nodeType||v.isWindow(e))return!1;try{if(e.constructor&&!p.call(e,"constructor")&&!p.call(e.constructor.prototype,"isPrototypeOf"))return!1}catch(n){return!1}var r;for(r in e);return r===t||p.call(e,r)},isEmptyObject:function(e){var t;for(t in e)return!1;return!0},error:function(e){throw new Error(e)},parseHTML:function(e,t,n){var r;return!e||typeof e!="string"?null:(typeof t=="boolean"&&(n=t,t=0),t=t||i,(r=E.exec(e))?[t.createElement(r[1])]:(r=v.buildFragment([e],t,n?null:[]),v.merge([],(r.cacheable?v.clone(r.fragment):r.fragment).childNodes)))},parseJSON:function(t){if(!t||typeof t!="string")return null;t=v.trim(t);if(e.JSON&&e.JSON.parse)return e.JSON.parse(t);if(S.test(t.replace(T,"@").replace(N,"]").replace(x,"")))return(new Function("return "+t))();v.error("Invalid JSON: "+t)},parseXML:function(n){var r,i;if(!n||typeof n!="string")return null;try{e.DOMParser?(i=new DOMParser,r=i.parseFromString(n,"text/xml")):(r=new ActiveXObject("Microsoft.XMLDOM"),r.async="false",r.loadXML(n))}catch(s){r=t}return(!r||!r.documentElement||r.getElementsByTagName("parsererror").length)&&v.error("Invalid XML: "+n),r},noop:function(){},globalEval:function(t){t&&g.test(t)&&(e.execScript||function(t){e.eval.call(e,t)})(t)},camelCase:function(e){return e.replace(C,"ms-").replace(k,L)},nodeName:function(e,t){return e.nodeName&&e.nodeName.toLowerCase()===t.toLowerCase()},each:function(e,n,r){var i,s=0,o=e.length,u=o===t||v.isFunction(e);if(r){if(u){for(i in e)if(n.apply(e[i],r)===!1)break}else for(;s0&&e[0]&&e[a-1]||a===0||v.isArray(e));if(f)for(;u-1)a.splice(n,1),i&&(n<=o&&o--,n<=u&&u--)}),this},has:function(e){return v.inArray(e,a)>-1},empty:function(){return a=[],this},disable:function(){return a=f=n=t,this},disabled:function(){return!a},lock:function(){return f=t,n||c.disable(),this},locked:function(){return!f},fireWith:function(e,t){return t=t||[],t=[e,t.slice?t.slice():t],a&&(!r||f)&&(i?f.push(t):l(t)),this},fire:function(){return c.fireWith(this,arguments),this},fired:function(){return!!r}};return c},v.extend({Deferred:function(e){var t=[["resolve","done",v.Callbacks("once memory"),"resolved"],["reject","fail",v.Callbacks("once memory"),"rejected"],["notify","progress",v.Callbacks("memory")]],n="pending",r={state:function(){return n},always:function(){return i.done(arguments).fail(arguments),this},then:function(){var e=arguments;return v.Deferred(function(n){v.each(t,function(t,r){var s=r[0],o=e[t];i[r[1]](v.isFunction(o)?function(){var e=o.apply(this,arguments);e&&v.isFunction(e.promise)?e.promise().done(n.resolve).fail(n.reject).progress(n.notify):n[s+"With"](this===i?n:this,[e])}:n[s])}),e=null}).promise()},promise:function(e){return e!=null?v.extend(e,r):r}},i={};return r.pipe=r.then,v.each(t,function(e,s){var o=s[2],u=s[3];r[s[1]]=o.add,u&&o.add(function(){n=u},t[e^1][2].disable,t[2][2].lock),i[s[0]]=o.fire,i[s[0]+"With"]=o.fireWith}),r.promise(i),e&&e.call(i,i),i},when:function(e){var t=0,n=l.call(arguments),r=n.length,i=r!==1||e&&v.isFunction(e.promise)?r:0,s=i===1?e:v.Deferred(),o=function(e,t,n){return function(r){t[e]=this,n[e]=arguments.length>1?l.call(arguments):r,n===u?s.notifyWith(t,n):--i||s.resolveWith(t,n)}},u,a,f;if(r>1){u=new Array(r),a=new Array(r),f=new Array(r);for(;t
    a",n=p.getElementsByTagName("*"),r=p.getElementsByTagName("a")[0];if(!n||!r||!n.length)return{};s=i.createElement("select"),o=s.appendChild(i.createElement("option")),u=p.getElementsByTagName("input")[0],r.style.cssText="top:1px;float:left;opacity:.5",t={leadingWhitespace:p.firstChild.nodeType===3,tbody:!p.getElementsByTagName("tbody").length,htmlSerialize:!!p.getElementsByTagName("link").length,style:/top/.test(r.getAttribute("style")),hrefNormalized:r.getAttribute("href")==="/a",opacity:/^0.5/.test(r.style.opacity),cssFloat:!!r.style.cssFloat,checkOn:u.value==="on",optSelected:o.selected,getSetAttribute:p.className!=="t",enctype:!!i.createElement("form").enctype,html5Clone:i.createElement("nav").cloneNode(!0).outerHTML!=="<:nav>",boxModel:i.compatMode==="CSS1Compat",submitBubbles:!0,changeBubbles:!0,focusinBubbles:!1,deleteExpando:!0,noCloneEvent:!0,inlineBlockNeedsLayout:!1,shrinkWrapBlocks:!1,reliableMarginRight:!0,boxSizingReliable:!0,pixelPosition:!1},u.checked=!0,t.noCloneChecked=u.cloneNode(!0).checked,s.disabled=!0,t.optDisabled=!o.disabled;try{delete p.test}catch(d){t.deleteExpando=!1}!p.addEventListener&&p.attachEvent&&p.fireEvent&&(p.attachEvent("onclick",h=function(){t.noCloneEvent=!1}),p.cloneNode(!0).fireEvent("onclick"),p.detachEvent("onclick",h)),u=i.createElement("input"),u.value="t",u.setAttribute("type","radio"),t.radioValue=u.value==="t",u.setAttribute("checked","checked"),u.setAttribute("name","t"),p.appendChild(u),a=i.createDocumentFragment(),a.appendChild(p.lastChild),t.checkClone=a.cloneNode(!0).cloneNode(!0).lastChild.checked,t.appendChecked=u.checked,a.removeChild(u),a.appendChild(p);if(p.attachEvent)for(l in{submit:!0,change:!0,focusin:!0})f="on"+l,c=f in p,c||(p.setAttribute(f,"return;"),c=typeof p[f]=="function"),t[l+"Bubbles"]=c;return v(function(){var n,r,s,o,u="padding:0;margin:0;border:0;display:block;overflow:hidden;",a=i.getElementsByTagName("body")[0];if(!a)return;n=i.createElement("div"),n.style.cssText="visibility:hidden;border:0;width:0;height:0;position:static;top:0;margin-top:1px",a.insertBefore(n,a.firstChild),r=i.createElement("div"),n.appendChild(r),r.innerHTML="
    t
    ",s=r.getElementsByTagName("td"),s[0].style.cssText="padding:0;margin:0;border:0;display:none",c=s[0].offsetHeight===0,s[0].style.display="",s[1].style.display="none",t.reliableHiddenOffsets=c&&s[0].offsetHeight===0,r.innerHTML="",r.style.cssText="box-sizing:border-box;-moz-box-sizing:border-box;-webkit-box-sizing:border-box;padding:1px;border:1px;display:block;width:4px;margin-top:1%;position:absolute;top:1%;",t.boxSizing=r.offsetWidth===4,t.doesNotIncludeMarginInBodyOffset=a.offsetTop!==1,e.getComputedStyle&&(t.pixelPosition=(e.getComputedStyle(r,null)||{}).top!=="1%",t.boxSizingReliable=(e.getComputedStyle(r,null)||{width:"4px"}).width==="4px",o=i.createElement("div"),o.style.cssText=r.style.cssText=u,o.style.marginRight=o.style.width="0",r.style.width="1px",r.appendChild(o),t.reliableMarginRight=!parseFloat((e.getComputedStyle(o,null)||{}).marginRight)),typeof r.style.zoom!="undefined"&&(r.innerHTML="",r.style.cssText=u+"width:1px;padding:1px;display:inline;zoom:1",t.inlineBlockNeedsLayout=r.offsetWidth===3,r.style.display="block",r.style.overflow="visible",r.innerHTML="
    ",r.firstChild.style.width="5px",t.shrinkWrapBlocks=r.offsetWidth!==3,n.style.zoom=1),a.removeChild(n),n=r=s=o=null}),a.removeChild(p),n=r=s=o=u=a=p=null,t}();var D=/(?:\{[\s\S]*\}|\[[\s\S]*\])$/,P=/([A-Z])/g;v.extend({cache:{},deletedIds:[],uuid:0,expando:"jQuery"+(v.fn.jquery+Math.random()).replace(/\D/g,""),noData:{embed:!0,object:"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000",applet:!0},hasData:function(e){return e=e.nodeType?v.cache[e[v.expando]]:e[v.expando],!!e&&!B(e)},data:function(e,n,r,i){if(!v.acceptData(e))return;var s,o,u=v.expando,a=typeof n=="string",f=e.nodeType,l=f?v.cache:e,c=f?e[u]:e[u]&&u;if((!c||!l[c]||!i&&!l[c].data)&&a&&r===t)return;c||(f?e[u]=c=v.deletedIds.pop()||v.guid++:c=u),l[c]||(l[c]={},f||(l[c].toJSON=v.noop));if(typeof n=="object"||typeof n=="function")i?l[c]=v.extend(l[c],n):l[c].data=v.extend(l[c].data,n);return s=l[c],i||(s.data||(s.data={}),s=s.data),r!==t&&(s[v.camelCase(n)]=r),a?(o=s[n],o==null&&(o=s[v.camelCase(n)])):o=s,o},removeData:function(e,t,n){if(!v.acceptData(e))return;var r,i,s,o=e.nodeType,u=o?v.cache:e,a=o?e[v.expando]:v.expando;if(!u[a])return;if(t){r=n?u[a]:u[a].data;if(r){v.isArray(t)||(t in r?t=[t]:(t=v.camelCase(t),t in r?t=[t]:t=t.split(" ")));for(i=0,s=t.length;i1,null,!1))},removeData:function(e){return this.each(function(){v.removeData(this,e)})}}),v.extend({queue:function(e,t,n){var r;if(e)return t=(t||"fx")+"queue",r=v._data(e,t),n&&(!r||v.isArray(n)?r=v._data(e,t,v.makeArray(n)):r.push(n)),r||[]},dequeue:function(e,t){t=t||"fx";var n=v.queue(e,t),r=n.length,i=n.shift(),s=v._queueHooks(e,t),o=function(){v.dequeue(e,t)};i==="inprogress"&&(i=n.shift(),r--),i&&(t==="fx"&&n.unshift("inprogress"),delete s.stop,i.call(e,o,s)),!r&&s&&s.empty.fire()},_queueHooks:function(e,t){var n=t+"queueHooks";return v._data(e,n)||v._data(e,n,{empty:v.Callbacks("once memory").add(function(){v.removeData(e,t+"queue",!0),v.removeData(e,n,!0)})})}}),v.fn.extend({queue:function(e,n){var r=2;return typeof e!="string"&&(n=e,e="fx",r--),arguments.length1)},removeAttr:function(e){return this.each(function(){v.removeAttr(this,e)})},prop:function(e,t){return v.access(this,v.prop,e,t,arguments.length>1)},removeProp:function(e){return e=v.propFix[e]||e,this.each(function(){try{this[e]=t,delete this[e]}catch(n){}})},addClass:function(e){var t,n,r,i,s,o,u;if(v.isFunction(e))return this.each(function(t){v(this).addClass(e.call(this,t,this.className))});if(e&&typeof e=="string"){t=e.split(y);for(n=0,r=this.length;n=0)r=r.replace(" "+n[s]+" "," ");i.className=e?v.trim(r):""}}}return this},toggleClass:function(e,t){var n=typeof e,r=typeof t=="boolean";return v.isFunction(e)?this.each(function(n){v(this).toggleClass(e.call(this,n,this.className,t),t)}):this.each(function(){if(n==="string"){var i,s=0,o=v(this),u=t,a=e.split(y);while(i=a[s++])u=r?u:!o.hasClass(i),o[u?"addClass":"removeClass"](i)}else if(n==="undefined"||n==="boolean")this.className&&v._data(this,"__className__",this.className),this.className=this.className||e===!1?"":v._data(this,"__className__")||""})},hasClass:function(e){var t=" "+e+" ",n=0,r=this.length;for(;n=0)return!0;return!1},val:function(e){var n,r,i,s=this[0];if(!arguments.length){if(s)return n=v.valHooks[s.type]||v.valHooks[s.nodeName.toLowerCase()],n&&"get"in n&&(r=n.get(s,"value"))!==t?r:(r=s.value,typeof r=="string"?r.replace(R,""):r==null?"":r);return}return i=v.isFunction(e),this.each(function(r){var s,o=v(this);if(this.nodeType!==1)return;i?s=e.call(this,r,o.val()):s=e,s==null?s="":typeof s=="number"?s+="":v.isArray(s)&&(s=v.map(s,function(e){return e==null?"":e+""})),n=v.valHooks[this.type]||v.valHooks[this.nodeName.toLowerCase()];if(!n||!("set"in n)||n.set(this,s,"value")===t)this.value=s})}}),v.extend({valHooks:{option:{get:function(e){var t=e.attributes.value;return!t||t.specified?e.value:e.text}},select:{get:function(e){var t,n,r=e.options,i=e.selectedIndex,s=e.type==="select-one"||i<0,o=s?null:[],u=s?i+1:r.length,a=i<0?u:s?i:0;for(;a=0}),n.length||(e.selectedIndex=-1),n}}},attrFn:{},attr:function(e,n,r,i){var s,o,u,a=e.nodeType;if(!e||a===3||a===8||a===2)return;if(i&&v.isFunction(v.fn[n]))return v(e)[n](r);if(typeof e.getAttribute=="undefined")return v.prop(e,n,r);u=a!==1||!v.isXMLDoc(e),u&&(n=n.toLowerCase(),o=v.attrHooks[n]||(X.test(n)?F:j));if(r!==t){if(r===null){v.removeAttr(e,n);return}return o&&"set"in o&&u&&(s=o.set(e,r,n))!==t?s:(e.setAttribute(n,r+""),r)}return o&&"get"in o&&u&&(s=o.get(e,n))!==null?s:(s=e.getAttribute(n),s===null?t:s)},removeAttr:function(e,t){var n,r,i,s,o=0;if(t&&e.nodeType===1){r=t.split(y);for(;o=0}})});var $=/^(?:textarea|input|select)$/i,J=/^([^\.]*|)(?:\.(.+)|)$/,K=/(?:^|\s)hover(\.\S+|)\b/,Q=/^key/,G=/^(?:mouse|contextmenu)|click/,Y=/^(?:focusinfocus|focusoutblur)$/,Z=function(e){return v.event.special.hover?e:e.replace(K,"mouseenter$1 mouseleave$1")};v.event={add:function(e,n,r,i,s){var o,u,a,f,l,c,h,p,d,m,g;if(e.nodeType===3||e.nodeType===8||!n||!r||!(o=v._data(e)))return;r.handler&&(d=r,r=d.handler,s=d.selector),r.guid||(r.guid=v.guid++),a=o.events,a||(o.events=a={}),u=o.handle,u||(o.handle=u=function(e){return typeof v=="undefined"||!!e&&v.event.triggered===e.type?t:v.event.dispatch.apply(u.elem,arguments)},u.elem=e),n=v.trim(Z(n)).split(" ");for(f=0;f=0&&(y=y.slice(0,-1),a=!0),y.indexOf(".")>=0&&(b=y.split("."),y=b.shift(),b.sort());if((!s||v.event.customEvent[y])&&!v.event.global[y])return;n=typeof n=="object"?n[v.expando]?n:new v.Event(y,n):new v.Event(y),n.type=y,n.isTrigger=!0,n.exclusive=a,n.namespace=b.join("."),n.namespace_re=n.namespace?new RegExp("(^|\\.)"+b.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,h=y.indexOf(":")<0?"on"+y:"";if(!s){u=v.cache;for(f in u)u[f].events&&u[f].events[y]&&v.event.trigger(n,r,u[f].handle.elem,!0);return}n.result=t,n.target||(n.target=s),r=r!=null?v.makeArray(r):[],r.unshift(n),p=v.event.special[y]||{};if(p.trigger&&p.trigger.apply(s,r)===!1)return;m=[[s,p.bindType||y]];if(!o&&!p.noBubble&&!v.isWindow(s)){g=p.delegateType||y,l=Y.test(g+y)?s:s.parentNode;for(c=s;l;l=l.parentNode)m.push([l,g]),c=l;c===(s.ownerDocument||i)&&m.push([c.defaultView||c.parentWindow||e,g])}for(f=0;f=0:v.find(h,this,null,[s]).length),u[h]&&f.push(c);f.length&&w.push({elem:s,matches:f})}d.length>m&&w.push({elem:this,matches:d.slice(m)});for(r=0;r0?this.on(t,null,e,n):this.trigger(t)},Q.test(t)&&(v.event.fixHooks[t]=v.event.keyHooks),G.test(t)&&(v.event.fixHooks[t]=v.event.mouseHooks)}),function(e,t){function nt(e,t,n,r){n=n||[],t=t||g;var i,s,a,f,l=t.nodeType;if(!e||typeof e!="string")return n;if(l!==1&&l!==9)return[];a=o(t);if(!a&&!r)if(i=R.exec(e))if(f=i[1]){if(l===9){s=t.getElementById(f);if(!s||!s.parentNode)return n;if(s.id===f)return n.push(s),n}else if(t.ownerDocument&&(s=t.ownerDocument.getElementById(f))&&u(t,s)&&s.id===f)return n.push(s),n}else{if(i[2])return S.apply(n,x.call(t.getElementsByTagName(e),0)),n;if((f=i[3])&&Z&&t.getElementsByClassName)return S.apply(n,x.call(t.getElementsByClassName(f),0)),n}return vt(e.replace(j,"$1"),t,n,r,a)}function rt(e){return function(t){var n=t.nodeName.toLowerCase();return n==="input"&&t.type===e}}function it(e){return function(t){var n=t.nodeName.toLowerCase();return(n==="input"||n==="button")&&t.type===e}}function st(e){return N(function(t){return t=+t,N(function(n,r){var i,s=e([],n.length,t),o=s.length;while(o--)n[i=s[o]]&&(n[i]=!(r[i]=n[i]))})})}function ot(e,t,n){if(e===t)return n;var r=e.nextSibling;while(r){if(r===t)return-1;r=r.nextSibling}return 1}function ut(e,t){var n,r,s,o,u,a,f,l=L[d][e+" "];if(l)return t?0:l.slice(0);u=e,a=[],f=i.preFilter;while(u){if(!n||(r=F.exec(u)))r&&(u=u.slice(r[0].length)||u),a.push(s=[]);n=!1;if(r=I.exec(u))s.push(n=new m(r.shift())),u=u.slice(n.length),n.type=r[0].replace(j," ");for(o in i.filter)(r=J[o].exec(u))&&(!f[o]||(r=f[o](r)))&&(s.push(n=new m(r.shift())),u=u.slice(n.length),n.type=o,n.matches=r);if(!n)break}return t?u.length:u?nt.error(e):L(e,a).slice(0)}function at(e,t,r){var i=t.dir,s=r&&t.dir==="parentNode",o=w++;return t.first?function(t,n,r){while(t=t[i])if(s||t.nodeType===1)return e(t,n,r)}:function(t,r,u){if(!u){var a,f=b+" "+o+" ",l=f+n;while(t=t[i])if(s||t.nodeType===1){if((a=t[d])===l)return t.sizset;if(typeof a=="string"&&a.indexOf(f)===0){if(t.sizset)return t}else{t[d]=l;if(e(t,r,u))return t.sizset=!0,t;t.sizset=!1}}}else while(t=t[i])if(s||t.nodeType===1)if(e(t,r,u))return t}}function ft(e){return e.length>1?function(t,n,r){var i=e.length;while(i--)if(!e[i](t,n,r))return!1;return!0}:e[0]}function lt(e,t,n,r,i){var s,o=[],u=0,a=e.length,f=t!=null;for(;u-1&&(s[f]=!(o[f]=c))}}else g=lt(g===o?g.splice(d,g.length):g),i?i(null,o,g,a):S.apply(o,g)})}function ht(e){var t,n,r,s=e.length,o=i.relative[e[0].type],u=o||i.relative[" "],a=o?1:0,f=at(function(e){return e===t},u,!0),l=at(function(e){return T.call(t,e)>-1},u,!0),h=[function(e,n,r){return!o&&(r||n!==c)||((t=n).nodeType?f(e,n,r):l(e,n,r))}];for(;a1&&ft(h),a>1&&e.slice(0,a-1).join("").replace(j,"$1"),n,a0,s=e.length>0,o=function(u,a,f,l,h){var p,d,v,m=[],y=0,w="0",x=u&&[],T=h!=null,N=c,C=u||s&&i.find.TAG("*",h&&a.parentNode||a),k=b+=N==null?1:Math.E;T&&(c=a!==g&&a,n=o.el);for(;(p=C[w])!=null;w++){if(s&&p){for(d=0;v=e[d];d++)if(v(p,a,f)){l.push(p);break}T&&(b=k,n=++o.el)}r&&((p=!v&&p)&&y--,u&&x.push(p))}y+=w;if(r&&w!==y){for(d=0;v=t[d];d++)v(x,m,a,f);if(u){if(y>0)while(w--)!x[w]&&!m[w]&&(m[w]=E.call(l));m=lt(m)}S.apply(l,m),T&&!u&&m.length>0&&y+t.length>1&&nt.uniqueSort(l)}return T&&(b=k,c=N),x};return o.el=0,r?N(o):o}function dt(e,t,n){var r=0,i=t.length;for(;r2&&(f=u[0]).type==="ID"&&t.nodeType===9&&!s&&i.relative[u[1].type]){t=i.find.ID(f.matches[0].replace($,""),t,s)[0];if(!t)return n;e=e.slice(u.shift().length)}for(o=J.POS.test(e)?-1:u.length-1;o>=0;o--){f=u[o];if(i.relative[l=f.type])break;if(c=i.find[l])if(r=c(f.matches[0].replace($,""),z.test(u[0].type)&&t.parentNode||t,s)){u.splice(o,1),e=r.length&&u.join("");if(!e)return S.apply(n,x.call(r,0)),n;break}}}return a(e,h)(r,t,s,n,z.test(e)),n}function mt(){}var n,r,i,s,o,u,a,f,l,c,h=!0,p="undefined",d=("sizcache"+Math.random()).replace(".",""),m=String,g=e.document,y=g.documentElement,b=0,w=0,E=[].pop,S=[].push,x=[].slice,T=[].indexOf||function(e){var t=0,n=this.length;for(;ti.cacheLength&&delete e[t.shift()],e[n+" "]=r},e)},k=C(),L=C(),A=C(),O="[\\x20\\t\\r\\n\\f]",M="(?:\\\\.|[-\\w]|[^\\x00-\\xa0])+",_=M.replace("w","w#"),D="([*^$|!~]?=)",P="\\["+O+"*("+M+")"+O+"*(?:"+D+O+"*(?:(['\"])((?:\\\\.|[^\\\\])*?)\\3|("+_+")|)|)"+O+"*\\]",H=":("+M+")(?:\\((?:(['\"])((?:\\\\.|[^\\\\])*?)\\2|([^()[\\]]*|(?:(?:"+P+")|[^:]|\\\\.)*|.*))\\)|)",B=":(even|odd|eq|gt|lt|nth|first|last)(?:\\("+O+"*((?:-\\d)?\\d*)"+O+"*\\)|)(?=[^-]|$)",j=new RegExp("^"+O+"+|((?:^|[^\\\\])(?:\\\\.)*)"+O+"+$","g"),F=new RegExp("^"+O+"*,"+O+"*"),I=new RegExp("^"+O+"*([\\x20\\t\\r\\n\\f>+~])"+O+"*"),q=new RegExp(H),R=/^(?:#([\w\-]+)|(\w+)|\.([\w\-]+))$/,U=/^:not/,z=/[\x20\t\r\n\f]*[+~]/,W=/:not\($/,X=/h\d/i,V=/input|select|textarea|button/i,$=/\\(?!\\)/g,J={ID:new RegExp("^#("+M+")"),CLASS:new RegExp("^\\.("+M+")"),NAME:new RegExp("^\\[name=['\"]?("+M+")['\"]?\\]"),TAG:new RegExp("^("+M.replace("w","w*")+")"),ATTR:new RegExp("^"+P),PSEUDO:new RegExp("^"+H),POS:new RegExp(B,"i"),CHILD:new RegExp("^:(only|nth|first|last)-child(?:\\("+O+"*(even|odd|(([+-]|)(\\d*)n|)"+O+"*(?:([+-]|)"+O+"*(\\d+)|))"+O+"*\\)|)","i"),needsContext:new RegExp("^"+O+"*[>+~]|"+B,"i")},K=function(e){var t=g.createElement("div");try{return e(t)}catch(n){return!1}finally{t=null}},Q=K(function(e){return e.appendChild(g.createComment("")),!e.getElementsByTagName("*").length}),G=K(function(e){return e.innerHTML="",e.firstChild&&typeof e.firstChild.getAttribute!==p&&e.firstChild.getAttribute("href")==="#"}),Y=K(function(e){e.innerHTML="";var t=typeof e.lastChild.getAttribute("multiple");return t!=="boolean"&&t!=="string"}),Z=K(function(e){return e.innerHTML="",!e.getElementsByClassName||!e.getElementsByClassName("e").length?!1:(e.lastChild.className="e",e.getElementsByClassName("e").length===2)}),et=K(function(e){e.id=d+0,e.innerHTML="
    ",y.insertBefore(e,y.firstChild);var t=g.getElementsByName&&g.getElementsByName(d).length===2+g.getElementsByName(d+0).length;return r=!g.getElementById(d),y.removeChild(e),t});try{x.call(y.childNodes,0)[0].nodeType}catch(tt){x=function(e){var t,n=[];for(;t=this[e];e++)n.push(t);return n}}nt.matches=function(e,t){return nt(e,null,null,t)},nt.matchesSelector=function(e,t){return nt(t,null,null,[e]).length>0},s=nt.getText=function(e){var t,n="",r=0,i=e.nodeType;if(i){if(i===1||i===9||i===11){if(typeof e.textContent=="string")return e.textContent;for(e=e.firstChild;e;e=e.nextSibling)n+=s(e)}else if(i===3||i===4)return e.nodeValue}else for(;t=e[r];r++)n+=s(t);return n},o=nt.isXML=function(e){var t=e&&(e.ownerDocument||e).documentElement;return t?t.nodeName!=="HTML":!1},u=nt.contains=y.contains?function(e,t){var n=e.nodeType===9?e.documentElement:e,r=t&&t.parentNode;return e===r||!!(r&&r.nodeType===1&&n.contains&&n.contains(r))}:y.compareDocumentPosition?function(e,t){return t&&!!(e.compareDocumentPosition(t)&16)}:function(e,t){while(t=t.parentNode)if(t===e)return!0;return!1},nt.attr=function(e,t){var n,r=o(e);return r||(t=t.toLowerCase()),(n=i.attrHandle[t])?n(e):r||Y?e.getAttribute(t):(n=e.getAttributeNode(t),n?typeof e[t]=="boolean"?e[t]?t:null:n.specified?n.value:null:null)},i=nt.selectors={cacheLength:50,createPseudo:N,match:J,attrHandle:G?{}:{href:function(e){return e.getAttribute("href",2)},type:function(e){return e.getAttribute("type")}},find:{ID:r?function(e,t,n){if(typeof t.getElementById!==p&&!n){var r=t.getElementById(e);return r&&r.parentNode?[r]:[]}}:function(e,n,r){if(typeof n.getElementById!==p&&!r){var i=n.getElementById(e);return i?i.id===e||typeof i.getAttributeNode!==p&&i.getAttributeNode("id").value===e?[i]:t:[]}},TAG:Q?function(e,t){if(typeof t.getElementsByTagName!==p)return t.getElementsByTagName(e)}:function(e,t){var n=t.getElementsByTagName(e);if(e==="*"){var r,i=[],s=0;for(;r=n[s];s++)r.nodeType===1&&i.push(r);return i}return n},NAME:et&&function(e,t){if(typeof t.getElementsByName!==p)return t.getElementsByName(name)},CLASS:Z&&function(e,t,n){if(typeof t.getElementsByClassName!==p&&!n)return t.getElementsByClassName(e)}},relative:{">":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(e){return e[1]=e[1].replace($,""),e[3]=(e[4]||e[5]||"").replace($,""),e[2]==="~="&&(e[3]=" "+e[3]+" "),e.slice(0,4)},CHILD:function(e){return e[1]=e[1].toLowerCase(),e[1]==="nth"?(e[2]||nt.error(e[0]),e[3]=+(e[3]?e[4]+(e[5]||1):2*(e[2]==="even"||e[2]==="odd")),e[4]=+(e[6]+e[7]||e[2]==="odd")):e[2]&&nt.error(e[0]),e},PSEUDO:function(e){var t,n;if(J.CHILD.test(e[0]))return null;if(e[3])e[2]=e[3];else if(t=e[4])q.test(t)&&(n=ut(t,!0))&&(n=t.indexOf(")",t.length-n)-t.length)&&(t=t.slice(0,n),e[0]=e[0].slice(0,n)),e[2]=t;return e.slice(0,3)}},filter:{ID:r?function(e){return e=e.replace($,""),function(t){return t.getAttribute("id")===e}}:function(e){return e=e.replace($,""),function(t){var n=typeof t.getAttributeNode!==p&&t.getAttributeNode("id");return n&&n.value===e}},TAG:function(e){return e==="*"?function(){return!0}:(e=e.replace($,"").toLowerCase(),function(t){return t.nodeName&&t.nodeName.toLowerCase()===e})},CLASS:function(e){var t=k[d][e+" "];return t||(t=new RegExp("(^|"+O+")"+e+"("+O+"|$)"))&&k(e,function(e){return t.test(e.className||typeof e.getAttribute!==p&&e.getAttribute("class")||"")})},ATTR:function(e,t,n){return function(r,i){var s=nt.attr(r,e);return s==null?t==="!=":t?(s+="",t==="="?s===n:t==="!="?s!==n:t==="^="?n&&s.indexOf(n)===0:t==="*="?n&&s.indexOf(n)>-1:t==="$="?n&&s.substr(s.length-n.length)===n:t==="~="?(" "+s+" ").indexOf(n)>-1:t==="|="?s===n||s.substr(0,n.length+1)===n+"-":!1):!0}},CHILD:function(e,t,n,r){return e==="nth"?function(e){var t,i,s=e.parentNode;if(n===1&&r===0)return!0;if(s){i=0;for(t=s.firstChild;t;t=t.nextSibling)if(t.nodeType===1){i++;if(e===t)break}}return i-=r,i===n||i%n===0&&i/n>=0}:function(t){var n=t;switch(e){case"only":case"first":while(n=n.previousSibling)if(n.nodeType===1)return!1;if(e==="first")return!0;n=t;case"last":while(n=n.nextSibling)if(n.nodeType===1)return!1;return!0}}},PSEUDO:function(e,t){var n,r=i.pseudos[e]||i.setFilters[e.toLowerCase()]||nt.error("unsupported pseudo: "+e);return r[d]?r(t):r.length>1?(n=[e,e,"",t],i.setFilters.hasOwnProperty(e.toLowerCase())?N(function(e,n){var i,s=r(e,t),o=s.length;while(o--)i=T.call(e,s[o]),e[i]=!(n[i]=s[o])}):function(e){return r(e,0,n)}):r}},pseudos:{not:N(function(e){var t=[],n=[],r=a(e.replace(j,"$1"));return r[d]?N(function(e,t,n,i){var s,o=r(e,null,i,[]),u=e.length;while(u--)if(s=o[u])e[u]=!(t[u]=s)}):function(e,i,s){return t[0]=e,r(t,null,s,n),!n.pop()}}),has:N(function(e){return function(t){return nt(e,t).length>0}}),contains:N(function(e){return function(t){return(t.textContent||t.innerText||s(t)).indexOf(e)>-1}}),enabled:function(e){return e.disabled===!1},disabled:function(e){return e.disabled===!0},checked:function(e){var t=e.nodeName.toLowerCase();return t==="input"&&!!e.checked||t==="option"&&!!e.selected},selected:function(e){return e.parentNode&&e.parentNode.selectedIndex,e.selected===!0},parent:function(e){return!i.pseudos.empty(e)},empty:function(e){var t;e=e.firstChild;while(e){if(e.nodeName>"@"||(t=e.nodeType)===3||t===4)return!1;e=e.nextSibling}return!0},header:function(e){return X.test(e.nodeName)},text:function(e){var t,n;return e.nodeName.toLowerCase()==="input"&&(t=e.type)==="text"&&((n=e.getAttribute("type"))==null||n.toLowerCase()===t)},radio:rt("radio"),checkbox:rt("checkbox"),file:rt("file"),password:rt("password"),image:rt("image"),submit:it("submit"),reset:it("reset"),button:function(e){var t=e.nodeName.toLowerCase();return t==="input"&&e.type==="button"||t==="button"},input:function(e){return V.test(e.nodeName)},focus:function(e){var t=e.ownerDocument;return e===t.activeElement&&(!t.hasFocus||t.hasFocus())&&!!(e.type||e.href||~e.tabIndex)},active:function(e){return e===e.ownerDocument.activeElement},first:st(function(){return[0]}),last:st(function(e,t){return[t-1]}),eq:st(function(e,t,n){return[n<0?n+t:n]}),even:st(function(e,t){for(var n=0;n=0;)e.push(r);return e}),gt:st(function(e,t,n){for(var r=n<0?n+t:n;++r",e.querySelectorAll("[selected]").length||i.push("\\["+O+"*(?:checked|disabled|ismap|multiple|readonly|selected|value)"),e.querySelectorAll(":checked").length||i.push(":checked")}),K(function(e){e.innerHTML="

    ",e.querySelectorAll("[test^='']").length&&i.push("[*^$]="+O+"*(?:\"\"|'')"),e.innerHTML="",e.querySelectorAll(":enabled").length||i.push(":enabled",":disabled")}),i=new RegExp(i.join("|")),vt=function(e,r,s,o,u){if(!o&&!u&&!i.test(e)){var a,f,l=!0,c=d,h=r,p=r.nodeType===9&&e;if(r.nodeType===1&&r.nodeName.toLowerCase()!=="object"){a=ut(e),(l=r.getAttribute("id"))?c=l.replace(n,"\\$&"):r.setAttribute("id",c),c="[id='"+c+"'] ",f=a.length;while(f--)a[f]=c+a[f].join("");h=z.test(e)&&r.parentNode||r,p=a.join(",")}if(p)try{return S.apply(s,x.call(h.querySelectorAll(p),0)),s}catch(v){}finally{l||r.removeAttribute("id")}}return t(e,r,s,o,u)},u&&(K(function(t){e=u.call(t,"div");try{u.call(t,"[test!='']:sizzle"),s.push("!=",H)}catch(n){}}),s=new RegExp(s.join("|")),nt.matchesSelector=function(t,n){n=n.replace(r,"='$1']");if(!o(t)&&!s.test(n)&&!i.test(n))try{var a=u.call(t,n);if(a||e||t.document&&t.document.nodeType!==11)return a}catch(f){}return nt(n,null,null,[t]).length>0})}(),i.pseudos.nth=i.pseudos.eq,i.filters=mt.prototype=i.pseudos,i.setFilters=new mt,nt.attr=v.attr,v.find=nt,v.expr=nt.selectors,v.expr[":"]=v.expr.pseudos,v.unique=nt.uniqueSort,v.text=nt.getText,v.isXMLDoc=nt.isXML,v.contains=nt.contains}(e);var nt=/Until$/,rt=/^(?:parents|prev(?:Until|All))/,it=/^.[^:#\[\.,]*$/,st=v.expr.match.needsContext,ot={children:!0,contents:!0,next:!0,prev:!0};v.fn.extend({find:function(e){var t,n,r,i,s,o,u=this;if(typeof e!="string")return v(e).filter(function(){for(t=0,n=u.length;t0)for(i=r;i=0:v.filter(e,this).length>0:this.filter(e).length>0)},closest:function(e,t){var n,r=0,i=this.length,s=[],o=st.test(e)||typeof e!="string"?v(e,t||this.context):0;for(;r-1:v.find.matchesSelector(n,e)){s.push(n);break}n=n.parentNode}}return s=s.length>1?v.unique(s):s,this.pushStack(s,"closest",e)},index:function(e){return e?typeof e=="string"?v.inArray(this[0],v(e)):v.inArray(e.jquery?e[0]:e,this):this[0]&&this[0].parentNode?this.prevAll().length:-1},add:function(e,t){var n=typeof e=="string"?v(e,t):v.makeArray(e&&e.nodeType?[e]:e),r=v.merge(this.get(),n);return this.pushStack(ut(n[0])||ut(r[0])?r:v.unique(r))},addBack:function(e){return this.add(e==null?this.prevObject:this.prevObject.filter(e))}}),v.fn.andSelf=v.fn.addBack,v.each({parent:function(e){var t=e.parentNode;return t&&t.nodeType!==11?t:null},parents:function(e){return v.dir(e,"parentNode")},parentsUntil:function(e,t,n){return v.dir(e,"parentNode",n)},next:function(e){return at(e,"nextSibling")},prev:function(e){return at(e,"previousSibling")},nextAll:function(e){return v.dir(e,"nextSibling")},prevAll:function(e){return v.dir(e,"previousSibling")},nextUntil:function(e,t,n){return v.dir(e,"nextSibling",n)},prevUntil:function(e,t,n){return v.dir(e,"previousSibling",n)},siblings:function(e){return v.sibling((e.parentNode||{}).firstChild,e)},children:function(e){return v.sibling(e.firstChild)},contents:function(e){return v.nodeName(e,"iframe")?e.contentDocument||e.contentWindow.document:v.merge([],e.childNodes)}},function(e,t){v.fn[e]=function(n,r){var i=v.map(this,t,n);return nt.test(e)||(r=n),r&&typeof r=="string"&&(i=v.filter(r,i)),i=this.length>1&&!ot[e]?v.unique(i):i,this.length>1&&rt.test(e)&&(i=i.reverse()),this.pushStack(i,e,l.call(arguments).join(","))}}),v.extend({filter:function(e,t,n){return n&&(e=":not("+e+")"),t.length===1?v.find.matchesSelector(t[0],e)?[t[0]]:[]:v.find.matches(e,t)},dir:function(e,n,r){var i=[],s=e[n];while(s&&s.nodeType!==9&&(r===t||s.nodeType!==1||!v(s).is(r)))s.nodeType===1&&i.push(s),s=s[n];return i},sibling:function(e,t){var n=[];for(;e;e=e.nextSibling)e.nodeType===1&&e!==t&&n.push(e);return n}});var ct="abbr|article|aside|audio|bdi|canvas|data|datalist|details|figcaption|figure|footer|header|hgroup|mark|meter|nav|output|progress|section|summary|time|video",ht=/ jQuery\d+="(?:null|\d+)"/g,pt=/^\s+/,dt=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/gi,vt=/<([\w:]+)/,mt=/]","i"),Et=/^(?:checkbox|radio)$/,St=/checked\s*(?:[^=]|=\s*.checked.)/i,xt=/\/(java|ecma)script/i,Tt=/^\s*\s*$/g,Nt={option:[1,""],legend:[1,"
    ","
    "],thead:[1,"","
    "],tr:[2,"","
    "],td:[3,"","
    "],col:[2,"","
    "],area:[1,"",""],_default:[0,"",""]},Ct=lt(i),kt=Ct.appendChild(i.createElement("div"));Nt.optgroup=Nt.option,Nt.tbody=Nt.tfoot=Nt.colgroup=Nt.caption=Nt.thead,Nt.th=Nt.td,v.support.htmlSerialize||(Nt._default=[1,"X
    ","
    "]),v.fn.extend({text:function(e){return v.access(this,function(e){return e===t?v.text(this):this.empty().append((this[0]&&this[0].ownerDocument||i).createTextNode(e))},null,e,arguments.length)},wrapAll:function(e){if(v.isFunction(e))return this.each(function(t){v(this).wrapAll(e.call(this,t))});if(this[0]){var t=v(e,this[0].ownerDocument).eq(0).clone(!0);this[0].parentNode&&t.insertBefore(this[0]),t.map(function(){var e=this;while(e.firstChild&&e.firstChild.nodeType===1)e=e.firstChild;return e}).append(this)}return this},wrapInner:function(e){return v.isFunction(e)?this.each(function(t){v(this).wrapInner(e.call(this,t))}):this.each(function(){var t=v(this),n=t.contents();n.length?n.wrapAll(e):t.append(e)})},wrap:function(e){var t=v.isFunction(e);return this.each(function(n){v(this).wrapAll(t?e.call(this,n):e)})},unwrap:function(){return this.parent().each(function(){v.nodeName(this,"body")||v(this).replaceWith(this.childNodes)}).end()},append:function(){return this.domManip(arguments,!0,function(e){(this.nodeType===1||this.nodeType===11)&&this.appendChild(e)})},prepend:function(){return this.domManip(arguments,!0,function(e){(this.nodeType===1||this.nodeType===11)&&this.insertBefore(e,this.firstChild)})},before:function(){if(!ut(this[0]))return this.domManip(arguments,!1,function(e){this.parentNode.insertBefore(e,this)});if(arguments.length){var e=v.clean(arguments);return this.pushStack(v.merge(e,this),"before",this.selector)}},after:function(){if(!ut(this[0]))return this.domManip(arguments,!1,function(e){this.parentNode.insertBefore(e,this.nextSibling)});if(arguments.length){var e=v.clean(arguments);return this.pushStack(v.merge(this,e),"after",this.selector)}},remove:function(e,t){var n,r=0;for(;(n=this[r])!=null;r++)if(!e||v.filter(e,[n]).length)!t&&n.nodeType===1&&(v.cleanData(n.getElementsByTagName("*")),v.cleanData([n])),n.parentNode&&n.parentNode.removeChild(n);return this},empty:function(){var e,t=0;for(;(e=this[t])!=null;t++){e.nodeType===1&&v.cleanData(e.getElementsByTagName("*"));while(e.firstChild)e.removeChild(e.firstChild)}return this},clone:function(e,t){return e=e==null?!1:e,t=t==null?e:t,this.map(function(){return v.clone(this,e,t)})},html:function(e){return v.access(this,function(e){var n=this[0]||{},r=0,i=this.length;if(e===t)return n.nodeType===1?n.innerHTML.replace(ht,""):t;if(typeof e=="string"&&!yt.test(e)&&(v.support.htmlSerialize||!wt.test(e))&&(v.support.leadingWhitespace||!pt.test(e))&&!Nt[(vt.exec(e)||["",""])[1].toLowerCase()]){e=e.replace(dt,"<$1>");try{for(;r1&&typeof f=="string"&&St.test(f))return this.each(function(){v(this).domManip(e,n,r)});if(v.isFunction(f))return this.each(function(i){var s=v(this);e[0]=f.call(this,i,n?s.html():t),s.domManip(e,n,r)});if(this[0]){i=v.buildFragment(e,this,l),o=i.fragment,s=o.firstChild,o.childNodes.length===1&&(o=s);if(s){n=n&&v.nodeName(s,"tr");for(u=i.cacheable||c-1;a0?this.clone(!0):this).get(),v(o[i])[t](r),s=s.concat(r);return this.pushStack(s,e,o.selector)}}),v.extend({clone:function(e,t,n){var r,i,s,o;v.support.html5Clone||v.isXMLDoc(e)||!wt.test("<"+e.nodeName+">")?o=e.cloneNode(!0):(kt.innerHTML=e.outerHTML,kt.removeChild(o=kt.firstChild));if((!v.support.noCloneEvent||!v.support.noCloneChecked)&&(e.nodeType===1||e.nodeType===11)&&!v.isXMLDoc(e)){Ot(e,o),r=Mt(e),i=Mt(o);for(s=0;r[s];++s)i[s]&&Ot(r[s],i[s])}if(t){At(e,o);if(n){r=Mt(e),i=Mt(o);for(s=0;r[s];++s)At(r[s],i[s])}}return r=i=null,o},clean:function(e,t,n,r){var s,o,u,a,f,l,c,h,p,d,m,g,y=t===i&&Ct,b=[];if(!t||typeof t.createDocumentFragment=="undefined")t=i;for(s=0;(u=e[s])!=null;s++){typeof u=="number"&&(u+="");if(!u)continue;if(typeof u=="string")if(!gt.test(u))u=t.createTextNode(u);else{y=y||lt(t),c=t.createElement("div"),y.appendChild(c),u=u.replace(dt,"<$1>"),a=(vt.exec(u)||["",""])[1].toLowerCase(),f=Nt[a]||Nt._default,l=f[0],c.innerHTML=f[1]+u+f[2];while(l--)c=c.lastChild;if(!v.support.tbody){h=mt.test(u),p=a==="table"&&!h?c.firstChild&&c.firstChild.childNodes:f[1]===""&&!h?c.childNodes:[];for(o=p.length-1;o>=0;--o)v.nodeName(p[o],"tbody")&&!p[o].childNodes.length&&p[o].parentNode.removeChild(p[o])}!v.support.leadingWhitespace&&pt.test(u)&&c.insertBefore(t.createTextNode(pt.exec(u)[0]),c.firstChild),u=c.childNodes,c.parentNode.removeChild(c)}u.nodeType?b.push(u):v.merge(b,u)}c&&(u=c=y=null);if(!v.support.appendChecked)for(s=0;(u=b[s])!=null;s++)v.nodeName(u,"input")?_t(u):typeof u.getElementsByTagName!="undefined"&&v.grep(u.getElementsByTagName("input"),_t);if(n){m=function(e){if(!e.type||xt.test(e.type))return r?r.push(e.parentNode?e.parentNode.removeChild(e):e):n.appendChild(e)};for(s=0;(u=b[s])!=null;s++)if(!v.nodeName(u,"script")||!m(u))n.appendChild(u),typeof u.getElementsByTagName!="undefined"&&(g=v.grep(v.merge([],u.getElementsByTagName("script")),m),b.splice.apply(b,[s+1,0].concat(g)),s+=g.length)}return b},cleanData:function(e,t){var n,r,i,s,o=0,u=v.expando,a=v.cache,f=v.support.deleteExpando,l=v.event.special;for(;(i=e[o])!=null;o++)if(t||v.acceptData(i)){r=i[u],n=r&&a[r];if(n){if(n.events)for(s in n.events)l[s]?v.event.remove(i,s):v.removeEvent(i,s,n.handle);a[r]&&(delete a[r],f?delete i[u]:i.removeAttribute?i.removeAttribute(u):i[u]=null,v.deletedIds.push(r))}}}}),function(){var e,t;v.uaMatch=function(e){e=e.toLowerCase();var t=/(chrome)[ \/]([\w.]+)/.exec(e)||/(webkit)[ \/]([\w.]+)/.exec(e)||/(opera)(?:.*version|)[ \/]([\w.]+)/.exec(e)||/(msie) ([\w.]+)/.exec(e)||e.indexOf("compatible")<0&&/(mozilla)(?:.*? rv:([\w.]+)|)/.exec(e)||[];return{browser:t[1]||"",version:t[2]||"0"}},e=v.uaMatch(o.userAgent),t={},e.browser&&(t[e.browser]=!0,t.version=e.version),t.chrome?t.webkit=!0:t.webkit&&(t.safari=!0),v.browser=t,v.sub=function(){function e(t,n){return new e.fn.init(t,n)}v.extend(!0,e,this),e.superclass=this,e.fn=e.prototype=this(),e.fn.constructor=e,e.sub=this.sub,e.fn.init=function(r,i){return i&&i instanceof v&&!(i instanceof e)&&(i=e(i)),v.fn.init.call(this,r,i,t)},e.fn.init.prototype=e.fn;var t=e(i);return e}}();var Dt,Pt,Ht,Bt=/alpha\([^)]*\)/i,jt=/opacity=([^)]*)/,Ft=/^(top|right|bottom|left)$/,It=/^(none|table(?!-c[ea]).+)/,qt=/^margin/,Rt=new RegExp("^("+m+")(.*)$","i"),Ut=new RegExp("^("+m+")(?!px)[a-z%]+$","i"),zt=new RegExp("^([-+])=("+m+")","i"),Wt={BODY:"block"},Xt={position:"absolute",visibility:"hidden",display:"block"},Vt={letterSpacing:0,fontWeight:400},$t=["Top","Right","Bottom","Left"],Jt=["Webkit","O","Moz","ms"],Kt=v.fn.toggle;v.fn.extend({css:function(e,n){return v.access(this,function(e,n,r){return r!==t?v.style(e,n,r):v.css(e,n)},e,n,arguments.length>1)},show:function(){return Yt(this,!0)},hide:function(){return Yt(this)},toggle:function(e,t){var n=typeof e=="boolean";return v.isFunction(e)&&v.isFunction(t)?Kt.apply(this,arguments):this.each(function(){(n?e:Gt(this))?v(this).show():v(this).hide()})}}),v.extend({cssHooks:{opacity:{get:function(e,t){if(t){var n=Dt(e,"opacity");return n===""?"1":n}}}},cssNumber:{fillOpacity:!0,fontWeight:!0,lineHeight:!0,opacity:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{"float":v.support.cssFloat?"cssFloat":"styleFloat"},style:function(e,n,r,i){if(!e||e.nodeType===3||e.nodeType===8||!e.style)return;var s,o,u,a=v.camelCase(n),f=e.style;n=v.cssProps[a]||(v.cssProps[a]=Qt(f,a)),u=v.cssHooks[n]||v.cssHooks[a];if(r===t)return u&&"get"in u&&(s=u.get(e,!1,i))!==t?s:f[n];o=typeof r,o==="string"&&(s=zt.exec(r))&&(r=(s[1]+1)*s[2]+parseFloat(v.css(e,n)),o="number");if(r==null||o==="number"&&isNaN(r))return;o==="number"&&!v.cssNumber[a]&&(r+="px");if(!u||!("set"in u)||(r=u.set(e,r,i))!==t)try{f[n]=r}catch(l){}},css:function(e,n,r,i){var s,o,u,a=v.camelCase(n);return n=v.cssProps[a]||(v.cssProps[a]=Qt(e.style,a)),u=v.cssHooks[n]||v.cssHooks[a],u&&"get"in u&&(s=u.get(e,!0,i)),s===t&&(s=Dt(e,n)),s==="normal"&&n in Vt&&(s=Vt[n]),r||i!==t?(o=parseFloat(s),r||v.isNumeric(o)?o||0:s):s},swap:function(e,t,n){var r,i,s={};for(i in t)s[i]=e.style[i],e.style[i]=t[i];r=n.call(e);for(i in t)e.style[i]=s[i];return r}}),e.getComputedStyle?Dt=function(t,n){var r,i,s,o,u=e.getComputedStyle(t,null),a=t.style;return u&&(r=u.getPropertyValue(n)||u[n],r===""&&!v.contains(t.ownerDocument,t)&&(r=v.style(t,n)),Ut.test(r)&&qt.test(n)&&(i=a.width,s=a.minWidth,o=a.maxWidth,a.minWidth=a.maxWidth=a.width=r,r=u.width,a.width=i,a.minWidth=s,a.maxWidth=o)),r}:i.documentElement.currentStyle&&(Dt=function(e,t){var n,r,i=e.currentStyle&&e.currentStyle[t],s=e.style;return i==null&&s&&s[t]&&(i=s[t]),Ut.test(i)&&!Ft.test(t)&&(n=s.left,r=e.runtimeStyle&&e.runtimeStyle.left,r&&(e.runtimeStyle.left=e.currentStyle.left),s.left=t==="fontSize"?"1em":i,i=s.pixelLeft+"px",s.left=n,r&&(e.runtimeStyle.left=r)),i===""?"auto":i}),v.each(["height","width"],function(e,t){v.cssHooks[t]={get:function(e,n,r){if(n)return e.offsetWidth===0&&It.test(Dt(e,"display"))?v.swap(e,Xt,function(){return tn(e,t,r)}):tn(e,t,r)},set:function(e,n,r){return Zt(e,n,r?en(e,t,r,v.support.boxSizing&&v.css(e,"boxSizing")==="border-box"):0)}}}),v.support.opacity||(v.cssHooks.opacity={get:function(e,t){return jt.test((t&&e.currentStyle?e.currentStyle.filter:e.style.filter)||"")?.01*parseFloat(RegExp.$1)+"":t?"1":""},set:function(e,t){var n=e.style,r=e.currentStyle,i=v.isNumeric(t)?"alpha(opacity="+t*100+")":"",s=r&&r.filter||n.filter||"";n.zoom=1;if(t>=1&&v.trim(s.replace(Bt,""))===""&&n.removeAttribute){n.removeAttribute("filter");if(r&&!r.filter)return}n.filter=Bt.test(s)?s.replace(Bt,i):s+" "+i}}),v(function(){v.support.reliableMarginRight||(v.cssHooks.marginRight={get:function(e,t){return v.swap(e,{display:"inline-block"},function(){if(t)return Dt(e,"marginRight")})}}),!v.support.pixelPosition&&v.fn.position&&v.each(["top","left"],function(e,t){v.cssHooks[t]={get:function(e,n){if(n){var r=Dt(e,t);return Ut.test(r)?v(e).position()[t]+"px":r}}}})}),v.expr&&v.expr.filters&&(v.expr.filters.hidden=function(e){return e.offsetWidth===0&&e.offsetHeight===0||!v.support.reliableHiddenOffsets&&(e.style&&e.style.display||Dt(e,"display"))==="none"},v.expr.filters.visible=function(e){return!v.expr.filters.hidden(e)}),v.each({margin:"",padding:"",border:"Width"},function(e,t){v.cssHooks[e+t]={expand:function(n){var r,i=typeof n=="string"?n.split(" "):[n],s={};for(r=0;r<4;r++)s[e+$t[r]+t]=i[r]||i[r-2]||i[0];return s}},qt.test(e)||(v.cssHooks[e+t].set=Zt)});var rn=/%20/g,sn=/\[\]$/,on=/\r?\n/g,un=/^(?:color|date|datetime|datetime-local|email|hidden|month|number|password|range|search|tel|text|time|url|week)$/i,an=/^(?:select|textarea)/i;v.fn.extend({serialize:function(){return v.param(this.serializeArray())},serializeArray:function(){return this.map(function(){return this.elements?v.makeArray(this.elements):this}).filter(function(){return this.name&&!this.disabled&&(this.checked||an.test(this.nodeName)||un.test(this.type))}).map(function(e,t){var n=v(this).val();return n==null?null:v.isArray(n)?v.map(n,function(e,n){return{name:t.name,value:e.replace(on,"\r\n")}}):{name:t.name,value:n.replace(on,"\r\n")}}).get()}}),v.param=function(e,n){var r,i=[],s=function(e,t){t=v.isFunction(t)?t():t==null?"":t,i[i.length]=encodeURIComponent(e)+"="+encodeURIComponent(t)};n===t&&(n=v.ajaxSettings&&v.ajaxSettings.traditional);if(v.isArray(e)||e.jquery&&!v.isPlainObject(e))v.each(e,function(){s(this.name,this.value)});else for(r in e)fn(r,e[r],n,s);return i.join("&").replace(rn,"+")};var ln,cn,hn=/#.*$/,pn=/^(.*?):[ \t]*([^\r\n]*)\r?$/mg,dn=/^(?:about|app|app\-storage|.+\-extension|file|res|widget):$/,vn=/^(?:GET|HEAD)$/,mn=/^\/\//,gn=/\?/,yn=/)<[^<]*)*<\/script>/gi,bn=/([?&])_=[^&]*/,wn=/^([\w\+\.\-]+:)(?:\/\/([^\/?#:]*)(?::(\d+)|)|)/,En=v.fn.load,Sn={},xn={},Tn=["*/"]+["*"];try{cn=s.href}catch(Nn){cn=i.createElement("a"),cn.href="",cn=cn.href}ln=wn.exec(cn.toLowerCase())||[],v.fn.load=function(e,n,r){if(typeof e!="string"&&En)return En.apply(this,arguments);if(!this.length)return this;var i,s,o,u=this,a=e.indexOf(" ");return a>=0&&(i=e.slice(a,e.length),e=e.slice(0,a)),v.isFunction(n)?(r=n,n=t):n&&typeof n=="object"&&(s="POST"),v.ajax({url:e,type:s,dataType:"html",data:n,complete:function(e,t){r&&u.each(r,o||[e.responseText,t,e])}}).done(function(e){o=arguments,u.html(i?v("
    ").append(e.replace(yn,"")).find(i):e)}),this},v.each("ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".split(" "),function(e,t){v.fn[t]=function(e){return this.on(t,e)}}),v.each(["get","post"],function(e,n){v[n]=function(e,r,i,s){return v.isFunction(r)&&(s=s||i,i=r,r=t),v.ajax({type:n,url:e,data:r,success:i,dataType:s})}}),v.extend({getScript:function(e,n){return v.get(e,t,n,"script")},getJSON:function(e,t,n){return v.get(e,t,n,"json")},ajaxSetup:function(e,t){return t?Ln(e,v.ajaxSettings):(t=e,e=v.ajaxSettings),Ln(e,t),e},ajaxSettings:{url:cn,isLocal:dn.test(ln[1]),global:!0,type:"GET",contentType:"application/x-www-form-urlencoded; charset=UTF-8",processData:!0,async:!0,accepts:{xml:"application/xml, text/xml",html:"text/html",text:"text/plain",json:"application/json, text/javascript","*":Tn},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText"},converters:{"* text":e.String,"text html":!0,"text json":v.parseJSON,"text xml":v.parseXML},flatOptions:{context:!0,url:!0}},ajaxPrefilter:Cn(Sn),ajaxTransport:Cn(xn),ajax:function(e,n){function T(e,n,s,a){var l,y,b,w,S,T=n;if(E===2)return;E=2,u&&clearTimeout(u),o=t,i=a||"",x.readyState=e>0?4:0,s&&(w=An(c,x,s));if(e>=200&&e<300||e===304)c.ifModified&&(S=x.getResponseHeader("Last-Modified"),S&&(v.lastModified[r]=S),S=x.getResponseHeader("Etag"),S&&(v.etag[r]=S)),e===304?(T="notmodified",l=!0):(l=On(c,w),T=l.state,y=l.data,b=l.error,l=!b);else{b=T;if(!T||e)T="error",e<0&&(e=0)}x.status=e,x.statusText=(n||T)+"",l?d.resolveWith(h,[y,T,x]):d.rejectWith(h,[x,T,b]),x.statusCode(g),g=t,f&&p.trigger("ajax"+(l?"Success":"Error"),[x,c,l?y:b]),m.fireWith(h,[x,T]),f&&(p.trigger("ajaxComplete",[x,c]),--v.active||v.event.trigger("ajaxStop"))}typeof e=="object"&&(n=e,e=t),n=n||{};var r,i,s,o,u,a,f,l,c=v.ajaxSetup({},n),h=c.context||c,p=h!==c&&(h.nodeType||h instanceof v)?v(h):v.event,d=v.Deferred(),m=v.Callbacks("once memory"),g=c.statusCode||{},b={},w={},E=0,S="canceled",x={readyState:0,setRequestHeader:function(e,t){if(!E){var n=e.toLowerCase();e=w[n]=w[n]||e,b[e]=t}return this},getAllResponseHeaders:function(){return E===2?i:null},getResponseHeader:function(e){var n;if(E===2){if(!s){s={};while(n=pn.exec(i))s[n[1].toLowerCase()]=n[2]}n=s[e.toLowerCase()]}return n===t?null:n},overrideMimeType:function(e){return E||(c.mimeType=e),this},abort:function(e){return e=e||S,o&&o.abort(e),T(0,e),this}};d.promise(x),x.success=x.done,x.error=x.fail,x.complete=m.add,x.statusCode=function(e){if(e){var t;if(E<2)for(t in e)g[t]=[g[t],e[t]];else t=e[x.status],x.always(t)}return this},c.url=((e||c.url)+"").replace(hn,"").replace(mn,ln[1]+"//"),c.dataTypes=v.trim(c.dataType||"*").toLowerCase().split(y),c.crossDomain==null&&(a=wn.exec(c.url.toLowerCase()),c.crossDomain=!(!a||a[1]===ln[1]&&a[2]===ln[2]&&(a[3]||(a[1]==="http:"?80:443))==(ln[3]||(ln[1]==="http:"?80:443)))),c.data&&c.processData&&typeof c.data!="string"&&(c.data=v.param(c.data,c.traditional)),kn(Sn,c,n,x);if(E===2)return x;f=c.global,c.type=c.type.toUpperCase(),c.hasContent=!vn.test(c.type),f&&v.active++===0&&v.event.trigger("ajaxStart");if(!c.hasContent){c.data&&(c.url+=(gn.test(c.url)?"&":"?")+c.data,delete c.data),r=c.url;if(c.cache===!1){var N=v.now(),C=c.url.replace(bn,"$1_="+N);c.url=C+(C===c.url?(gn.test(c.url)?"&":"?")+"_="+N:"")}}(c.data&&c.hasContent&&c.contentType!==!1||n.contentType)&&x.setRequestHeader("Content-Type",c.contentType),c.ifModified&&(r=r||c.url,v.lastModified[r]&&x.setRequestHeader("If-Modified-Since",v.lastModified[r]),v.etag[r]&&x.setRequestHeader("If-None-Match",v.etag[r])),x.setRequestHeader("Accept",c.dataTypes[0]&&c.accepts[c.dataTypes[0]]?c.accepts[c.dataTypes[0]]+(c.dataTypes[0]!=="*"?", "+Tn+"; q=0.01":""):c.accepts["*"]);for(l in c.headers)x.setRequestHeader(l,c.headers[l]);if(!c.beforeSend||c.beforeSend.call(h,x,c)!==!1&&E!==2){S="abort";for(l in{success:1,error:1,complete:1})x[l](c[l]);o=kn(xn,c,n,x);if(!o)T(-1,"No Transport");else{x.readyState=1,f&&p.trigger("ajaxSend",[x,c]),c.async&&c.timeout>0&&(u=setTimeout(function(){x.abort("timeout")},c.timeout));try{E=1,o.send(b,T)}catch(k){if(!(E<2))throw k;T(-1,k)}}return x}return x.abort()},active:0,lastModified:{},etag:{}});var Mn=[],_n=/\?/,Dn=/(=)\?(?=&|$)|\?\?/,Pn=v.now();v.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var e=Mn.pop()||v.expando+"_"+Pn++;return this[e]=!0,e}}),v.ajaxPrefilter("json jsonp",function(n,r,i){var s,o,u,a=n.data,f=n.url,l=n.jsonp!==!1,c=l&&Dn.test(f),h=l&&!c&&typeof a=="string"&&!(n.contentType||"").indexOf("application/x-www-form-urlencoded")&&Dn.test(a);if(n.dataTypes[0]==="jsonp"||c||h)return s=n.jsonpCallback=v.isFunction(n.jsonpCallback)?n.jsonpCallback():n.jsonpCallback,o=e[s],c?n.url=f.replace(Dn,"$1"+s):h?n.data=a.replace(Dn,"$1"+s):l&&(n.url+=(_n.test(f)?"&":"?")+n.jsonp+"="+s),n.converters["script json"]=function(){return u||v.error(s+" was not called"),u[0]},n.dataTypes[0]="json",e[s]=function(){u=arguments},i.always(function(){e[s]=o,n[s]&&(n.jsonpCallback=r.jsonpCallback,Mn.push(s)),u&&v.isFunction(o)&&o(u[0]),u=o=t}),"script"}),v.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/javascript|ecmascript/},converters:{"text script":function(e){return v.globalEval(e),e}}}),v.ajaxPrefilter("script",function(e){e.cache===t&&(e.cache=!1),e.crossDomain&&(e.type="GET",e.global=!1)}),v.ajaxTransport("script",function(e){if(e.crossDomain){var n,r=i.head||i.getElementsByTagName("head")[0]||i.documentElement;return{send:function(s,o){n=i.createElement("script"),n.async="async",e.scriptCharset&&(n.charset=e.scriptCharset),n.src=e.url,n.onload=n.onreadystatechange=function(e,i){if(i||!n.readyState||/loaded|complete/.test(n.readyState))n.onload=n.onreadystatechange=null,r&&n.parentNode&&r.removeChild(n),n=t,i||o(200,"success")},r.insertBefore(n,r.firstChild)},abort:function(){n&&n.onload(0,1)}}}});var Hn,Bn=e.ActiveXObject?function(){for(var e in Hn)Hn[e](0,1)}:!1,jn=0;v.ajaxSettings.xhr=e.ActiveXObject?function(){return!this.isLocal&&Fn()||In()}:Fn,function(e){v.extend(v.support,{ajax:!!e,cors:!!e&&"withCredentials"in e})}(v.ajaxSettings.xhr()),v.support.ajax&&v.ajaxTransport(function(n){if(!n.crossDomain||v.support.cors){var r;return{send:function(i,s){var o,u,a=n.xhr();n.username?a.open(n.type,n.url,n.async,n.username,n.password):a.open(n.type,n.url,n.async);if(n.xhrFields)for(u in n.xhrFields)a[u]=n.xhrFields[u];n.mimeType&&a.overrideMimeType&&a.overrideMimeType(n.mimeType),!n.crossDomain&&!i["X-Requested-With"]&&(i["X-Requested-With"]="XMLHttpRequest");try{for(u in i)a.setRequestHeader(u,i[u])}catch(f){}a.send(n.hasContent&&n.data||null),r=function(e,i){var u,f,l,c,h;try{if(r&&(i||a.readyState===4)){r=t,o&&(a.onreadystatechange=v.noop,Bn&&delete Hn[o]);if(i)a.readyState!==4&&a.abort();else{u=a.status,l=a.getAllResponseHeaders(),c={},h=a.responseXML,h&&h.documentElement&&(c.xml=h);try{c.text=a.responseText}catch(p){}try{f=a.statusText}catch(p){f=""}!u&&n.isLocal&&!n.crossDomain?u=c.text?200:404:u===1223&&(u=204)}}}catch(d){i||s(-1,d)}c&&s(u,f,c,l)},n.async?a.readyState===4?setTimeout(r,0):(o=++jn,Bn&&(Hn||(Hn={},v(e).unload(Bn)),Hn[o]=r),a.onreadystatechange=r):r()},abort:function(){r&&r(0,1)}}}});var qn,Rn,Un=/^(?:toggle|show|hide)$/,zn=new RegExp("^(?:([-+])=|)("+m+")([a-z%]*)$","i"),Wn=/queueHooks$/,Xn=[Gn],Vn={"*":[function(e,t){var n,r,i=this.createTween(e,t),s=zn.exec(t),o=i.cur(),u=+o||0,a=1,f=20;if(s){n=+s[2],r=s[3]||(v.cssNumber[e]?"":"px");if(r!=="px"&&u){u=v.css(i.elem,e,!0)||n||1;do a=a||".5",u/=a,v.style(i.elem,e,u+r);while(a!==(a=i.cur()/o)&&a!==1&&--f)}i.unit=r,i.start=u,i.end=s[1]?u+(s[1]+1)*n:n}return i}]};v.Animation=v.extend(Kn,{tweener:function(e,t){v.isFunction(e)?(t=e,e=["*"]):e=e.split(" ");var n,r=0,i=e.length;for(;r-1,f={},l={},c,h;a?(l=i.position(),c=l.top,h=l.left):(c=parseFloat(o)||0,h=parseFloat(u)||0),v.isFunction(t)&&(t=t.call(e,n,s)),t.top!=null&&(f.top=t.top-s.top+c),t.left!=null&&(f.left=t.left-s.left+h),"using"in t?t.using.call(e,f):i.css(f)}},v.fn.extend({position:function(){if(!this[0])return;var e=this[0],t=this.offsetParent(),n=this.offset(),r=er.test(t[0].nodeName)?{top:0,left:0}:t.offset();return n.top-=parseFloat(v.css(e,"marginTop"))||0,n.left-=parseFloat(v.css(e,"marginLeft"))||0,r.top+=parseFloat(v.css(t[0],"borderTopWidth"))||0,r.left+=parseFloat(v.css(t[0],"borderLeftWidth"))||0,{top:n.top-r.top,left:n.left-r.left}},offsetParent:function(){return this.map(function(){var e=this.offsetParent||i.body;while(e&&!er.test(e.nodeName)&&v.css(e,"position")==="static")e=e.offsetParent;return e||i.body})}}),v.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(e,n){var r=/Y/.test(n);v.fn[e]=function(i){return v.access(this,function(e,i,s){var o=tr(e);if(s===t)return o?n in o?o[n]:o.document.documentElement[i]:e[i];o?o.scrollTo(r?v(o).scrollLeft():s,r?s:v(o).scrollTop()):e[i]=s},e,i,arguments.length,null)}}),v.each({Height:"height",Width:"width"},function(e,n){v.each({padding:"inner"+e,content:n,"":"outer"+e},function(r,i){v.fn[i]=function(i,s){var o=arguments.length&&(r||typeof i!="boolean"),u=r||(i===!0||s===!0?"margin":"border");return v.access(this,function(n,r,i){var s;return v.isWindow(n)?n.document.documentElement["client"+e]:n.nodeType===9?(s=n.documentElement,Math.max(n.body["scroll"+e],s["scroll"+e],n.body["offset"+e],s["offset"+e],s["client"+e])):i===t?v.css(n,r,i,u):v.style(n,r,i,u)},n,o?i:t,o,null)}})}),e.jQuery=e.$=v,typeof define=="function"&&define.amd&&define.amd.jQuery&&define("jquery",[],function(){return v})})(window); \ No newline at end of file diff --git a/retro/static/2013/konami.min.e165c814457d.js b/retro/static/2013/konami.min.e165c814457d.js new file mode 100644 index 00000000..f69ca4ff --- /dev/null +++ b/retro/static/2013/konami.min.e165c814457d.js @@ -0,0 +1,4 @@ +var Konami=function(t){var e={addEvent:function(t,e,n,i){t.addEventListener?t.addEventListener(e,n,!1):t.attachEvent&&(t["e"+e+n]=n,t[e+n]=function(){t["e"+e+n](window.event,i)},t.attachEvent("on"+e,t[e+n]))},input:"",pattern:"3838404037393739666513",load:function(t){this.addEvent(document,"keydown",function(n,i){return i&&(e=i),e.input+=n?n.keyCode:event.keyCode,e.input.length>e.pattern.length&&(e.input=e.input.substr(e.input.length-e.pattern.length)),e.input==e.pattern?(e.code(t),e.input="",void 0):void 0},this),this.iphone.load(t)},code:function(t){window.location=t},iphone:{start_x:0,start_y:0,stop_x:0,stop_y:0,tap:!1,capture:!1,orig_keys:"",keys:["UP","UP","DOWN","DOWN","LEFT","RIGHT","LEFT","RIGHT","TAP","TAP","TAP"],code:function(t){e.code(t)},load:function(t){this.orig_keys=this.keys,e.addEvent(document,"touchmove",function(t){if(1==t.touches.length&&e.iphone.capture===!0){var n=t.touches[0] + e.iphone.stop_x=n.pageX,e.iphone.stop_y=n.pageY,e.iphone.tap=!1,e.iphone.capture=!1,e.iphone.check_direction()}}),e.addEvent(document,"touchend",function(){e.iphone.tap===!0&&e.iphone.check_direction(t)},!1),e.addEvent(document,"touchstart",function(t){e.iphone.start_x=t.changedTouches[0].pageX,e.iphone.start_y=t.changedTouches[0].pageY,e.iphone.tap=!0,e.iphone.capture=!0})},check_direction:function(t){var e=Math.abs(this.start_x-this.stop_x),n=Math.abs(this.start_y-this.stop_y),i=0>this.start_x-this.stop_x?"RIGHT":"LEFT",o=0>this.start_y-this.stop_y?"DOWN":"UP",s=e>n?i:o + s=this.tap===!0?"TAP":s,s==this.keys[0]&&(this.keys=this.keys.slice(1,this.keys.length)),0==this.keys.length&&(this.keys=this.orig_keys,this.code(t))}}} +return"string"==typeof t&&e.load(t),"function"==typeof t&&(e.code=t,e.load()),e} diff --git a/retro/static/2013/rss.c5ebdc5318d6.png b/retro/static/2013/rss.c5ebdc5318d6.png new file mode 120000 index 00000000..094d5953 --- /dev/null +++ b/retro/static/2013/rss.c5ebdc5318d6.png @@ -0,0 +1 @@ +rss.png \ No newline at end of file diff --git a/retro/static/2013/rss.png b/retro/static/2013/rss.png new file mode 100644 index 00000000..a6f114cd Binary files /dev/null and b/retro/static/2013/rss.png differ diff --git a/retro/static/2013/vector_tux.864e6cdcc23e.png b/retro/static/2013/vector_tux.864e6cdcc23e.png new file mode 100644 index 00000000..ab4be6d0 Binary files /dev/null and b/retro/static/2013/vector_tux.864e6cdcc23e.png differ diff --git a/retro/static/2013/vnet_button.png b/retro/static/2013/vnet_button.png new file mode 100644 index 00000000..22cfa9e4 Binary files /dev/null and b/retro/static/2013/vnet_button.png differ diff --git a/retro/templates/retro/index-2012-03-09.html b/retro/templates/retro/index-2012-03-09.html new file mode 100644 index 00000000..e130b97f --- /dev/null +++ b/retro/templates/retro/index-2012-03-09.html @@ -0,0 +1,485 @@ +{% load retro_static from retro %} + + Arch Linux + + + + + + + + + + + + + + + +
    + +
    + +
    +
    + +
    +
    + +
    + + + + +
    +
    + + +
    + +

    A simple, lightweight distribution

    + +

    You've reached the website for Arch Linux, a + lightweight and flexible Linux® distribution that tries to Keep It + Simple.

    + +

    Currently we have official packages optimized for the i686 and + x86-64 architectures. We complement our official package sets with a + + community-operated package repository that grows in size and + quality each and every day.

    + +

    Our strong community is diverse and helpful, and we pride ourselves + on the range of skillsets and uses for Arch that stem from it. Please + check out our forums + and mailing lists + to get your feet wet. Also glance through our wiki + if you want to learn more about Arch.

    + +

    Learn more...

    + +
    + +
    + +

    + Latest News + +

    + + RSS Feed + + + +

    + Minimum kernel requirement 2.6.32 +

    +

    2012-02-07

    +

    From the glibc-2.15-5 package, the minimum required kernel version will +be increased from 2.6.27 to 2.6.32. This reflects the oldest kernel +version still receiving updates upstream.

    + + + +

    + libpng/libtiff rebuilds move from [testing] +

    +

    2012-02-05

    +

    Recent releases of libpng and libtiff have required a rebuild of all +packages that depend on them; these have just been moved from [testing] +to the main repos. As usual, remember to fully update your system and +check your unofficial packages (especially the cairo-* packages from +AUR) for required rebuilds.

    +

    The update might output messages similar to:

    +
    g_module_open() failed for /usr/lib/gdk-pixbuf-2.0/2.10.0/loaders/libpixbufloader-svg.so:
    +libpng14.so.14: cannot open ...
    + + + +

    + Arch Linux @ FOSDEM 2012 +

    +

    2012-01-23

    +

    The FOSDEM conference takes place on 4/5 February in Brussels, Belgium and our attendance this year is bigger than ever. +On the list of Archers coming we find developers Роман Кирилич (Roman Kyrylych), Tom Gundersen, Thomas Bächler, Jan Steffens, Pierre Schmitz and myself.

    +

    We're putting together meetups on Friday afternoon, evening and +Saturday evening. Our program is not definitive yet, so to stay up to +date (or make suggestions) check the wiki page ...

    + + + +

    + kmod replaces module-init-tools +

    +

    2012-01-21

    +

    With module-init-tools being +declared a dead project by its current maintainer, a new project has +stepped up to take its place: kmod. This is intended to be a drop-in +replacement, though deprecated functionality in module-init-tools has +not been reimplemented.

    +

    If, upon upgrade, pacman moves /etc/modprobe.d/modprobe.conf + to a .pacsave, you should move it back. This file, and any other config + read by module-init-tools, is still read by kmod. However, the kmod +package ...

    + + + +

    + pacman 4 moves to [core] +

    +

    2012-01-16

    +

    Pacman 4 has landed in [core]! Thanks to 24 contributors producing 893 commits, you'll find many new features. + The one explicitly worth calling out is PGP signing. However, until the + last few details regarding database signing and keyring distribution +are ironed out, this is disabled in pacman's default config. If you're +interested trying out package verification, please refer to the +documentation on the wiki about pacman-key or Allan's blog post.

    +

    As ...

    + + + + +

    + Older News + +

    +
    + +
    2012-01-02
    +
    + Users of unofficial kernels must enable devtmpfs support +
    + + + + + +
    2011-12-20
    +
    + filesystem upgrade - manual intervention required +
    + + + + + +
    2011-10-24
    +
    + wiki and bbs downtime +
    + + + + + +
    2011-10-22
    +
    + initscripts update - manual intervention required +
    + + + + + +
    2011-10-06
    +
    + Hostname utility moved from net-tools to inetutils +
    + + + + + +
    2011-10-01
    +
    + GNOME 3.2.0 in extra +
    + + + + + +
    2011-09-15
    +
    + TeXLive 2011 update +
    + + + + + +
    2011-08-20
    +
    + 2011.08.19 installation media +
    + + + + + +
    2011-08-14
    +
    + Bug day: Sunday, August 21st +
    + + + + + +
    2011-08-07
    +
    + Changes to kernel package and filenames +
    + +
    + + + + +
    + + +
    +
    + +
    + + +
    + +
    +
    + + +
    + + +
    + +
    + +

    Recent Updates (more)

    + + RSS Feed + +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    samba 3.6.3-3 + i686/x86_64 +
    nvidia-lts 295.20-2 + i686/x86_64 +
    linux-lts 3.0.23-1 + i686/x86_64 +
    nfs-utils 1.2.5-2 + i686/x86_64 +
    blueman 1.23-3 + i686/x86_64 +
    freetype2 2.4.9-1 + i686/x86_64 +
    midori 0.4.4-1 + i686/x86_64 +
    ext4magic 0.3.0-1 + i686/x86_64 +
    python-sqlalchemy 0.7.5-1 + i686/x86_64 +
    subversion 1.7.4-1 + i686/x86_64 +
    krb5 1.10.1-1 + i686/x86_64 +
    libcroco 0.6.4-1 + i686/x86_64 +
    gif2png 2.5.7-1 + i686/x86_64 +
    clementine 1.0.1-3 + i686/x86_64 +
    libgphoto2 2.4.13-1 + i686/x86_64 +
    + + + + + + + + + + + + + + + + + diff --git a/retro/templates/retro/index-2013-03-07.html b/retro/templates/retro/index-2013-03-07.html new file mode 100644 index 00000000..10e7002d --- /dev/null +++ b/retro/templates/retro/index-2013-03-07.html @@ -0,0 +1,482 @@ +{% load retro_static from retro %} + + + Arch Linux + + + + + + + + + + + + + + +
    + +
    + +
    +
    +
    +
    + +
    + + +
    +
    + + +
    +

    A simple, lightweight distribution

    + +

    You've reached the website for Arch Linux, a + lightweight and flexible Linux® distribution that tries to Keep It + Simple.

    + +

    Currently we have official packages optimized for the i686 and + x86-64 architectures. We complement our official package sets with a + + community-operated package repository that grows in size and + quality each and every day.

    + +

    Our strong community is diverse and helpful, and we pride ourselves + on the range of skillsets and uses for Arch that stem from it. Please + check out our forums + and mailing lists + to get your feet wet. Also glance through our wiki + if you want to learn more about Arch.

    + +

    Learn more...

    +
    + +
    +

    + Latest News + +

    + + RSS Feed + + +

    + MariaDB replaces MySQL in repositories +

    +

    2013-03-25

    +
    +

    MariaDB is now officially our default implementation of MySQL. MariaDB is almost + a drop in replacement, so an upgrade should be possible with minimum +hassle. However, due to remaining compatibility concerns, an automatic +replace is not done.

    +

    It is recommended for all users to upgrade. MySQL will be dropped from the repositories to the AUR in a month.

    +

    Users who want to switch will need to install mariadb, libmariadbclient or mariadb-clients and execute mysql_upgrade in order to migrate their systems.

    +

    Migration example:

    +
    # systemctl stop mysqld
    +# pacman -S mariadb libmariadbclient mariadb-clients
    +# systemctl start mysqld
    +# mysql_upgrade -p
    +
    +

    percona-server is another MySQL fork available in +[community]. It should be closer to Oracle MySQL Enterprise, but is +missing the new features included in MariaDB.

    +

    Together with mysql 5.5.30-7 in [extra], all packages +depending on it have been rebuilt against their MariaDB counterparts. +Other package maintainers should move their dependencies to the MariaDB +packages.

    +

    More information can be found on our mailing list.

    + +
    + +

    + qt4 replaces qt +

    +

    2013-03-01

    +
    +

    A new qt4 package is in [extra]. This replaces the current qt package.

    +

    All packages depending on qt need to be rebuilt to depend on qt4. We have done this for all official packages, but you will need to rebuild packages installed from the AUR that depend on qt.

    +

    Qt 5.x is now also available in [extra]. When you install both qt5-base and qt4 + any Qt tool will refer to the 5.x version. We provide *-qt4 symlinks so + you can explicitly force the 4.x version when you need it.

    +
    + +

    + Changes to LVM +

    +

    2013-02-12

    +
    +

    With lvm2 2.02.98-3, we now utilize lvmetad to activate LVM volumes automatically. This implies the following changes:

    +
      +
    • The lvm2 initramfs hook now requires the udev hook.
    • +
    • The use_lvmetad = 1 must be set in /etc/lvm/lvm.conf. This is the default now - if you have a lvm.conf.pacnew file, you must merge this change.
    • +
    • You can restrict the volumes that are activated automatically by setting the auto_activation_volume_list in /etc/lvm/lvm.conf. If in doubt, leave this option commented out.
    • +
    • If you need monitoring (needed for snapshots), run systemctl enable lvm-monitoring.service.
    • +
    • The lvmwait kernel command line ...
    +
    + +

    + Final sysvinit deprecation warning +

    +

    2013-02-04

    +
    +

    As previously announced, initscripts are no longer receiving any +testing and support has been dropped from various packages. Any users +still using them should switch to systemd.

    +

    initscripts, sysvinit and the various rc scripts are being removed +from the repositories to avoid any confusion about their status.

    +
    + +

    + Update filesystem-2013.01-1 and glibc-2.17-2 together +

    +

    2013-01-26

    +
    +

    Due to moving of the /lib symlink from the glibc package to the more +appropriate filesystem package, it is required to update glibc-2.17-2 +and filesystem-2013.01-1 together. This will happen automatically when +you run "pacman -Syu". Remember, partial updates are not supported and never use the "--force" option...

    +

    A potential issue with the upgrade on x86_64 is finding conflicting +files in /usr/lib64. All Arch Linux packages that had files in this +directory have been updated, so update these individually first. Any +AUR packages with files in this directory should be updated to install +them in /usr/lib.

    +
    + +

    + Older News + +

    +
    + +
    2012-12-01
    +
    + December: time for a new install medium +
    + + +
    2012-11-04
    +
    + End of initscripts support +
    + + +
    2012-11-02
    +
    + November release of install media available +
    + + +
    2012-11-01
    +
    + Bug Squashing Day: Saturday 17th November +
    + + +
    2012-10-30
    +
    + ConsoleKit replaced by logind +
    + + +
    2012-10-13
    +
    + systemd is now the default on new installations +
    + + +
    2012-10-07
    +
    + Install medium 2012.10.06 introduces systemd +
    + + +
    2012-09-08
    +
    + New install medium 2012.09.07 +
    + + +
    2012-09-06
    +
    + Fontconfig 2.10.1 update - manual intervention required +
    + + +
    2012-08-11
    +
    + netcfg-2.8.9 drops deprecated rc.conf compatibility +
    +
    + +
    + + +
    +
    +
    + + +
    +
    +
    + + +
    +
    +
    + +
    +

    Recent Updates (more)

    + + RSS Feed + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    firefox 20.0-1 + i686/x86_64 +
    firefox-i18n 20.0-1 + any +
    nvidia-utils 313.26-3 + i686/x86_64 +
    rust 0.6-1 + i686/x86_64 +
    murmur 1.2.3-13 + i686/x86_64 +
    0ad a13-1 + i686/x86_64 +
    0ad-data a13-1 + any +
    nginx 1.2.8-1 + i686/x86_64 +
    sxiv 1.1-2 + i686/x86_64 +
    vtk 5.10.1-7 + i686/x86_64 +
    openmpi 1.6.4-2 + i686/x86_64 +
    hexchat 2.9.5-3 + i686/x86_64 +
    libwebp 0.3.0-1 + i686/x86_64 +
    pcsc-perl 1.4.13-1 + i686/x86_64 +
    live-media 2013.04.01-1 + i686/x86_64 +
    +
    + + + + + + + + + + +
    + + +
    + + + + + + +
      diff --git a/retro/views.py b/retro/views.py index 31226deb..7301a97e 100644 --- a/retro/views.py +++ b/retro/views.py @@ -14,6 +14,8 @@ 2009: 'index-20090327.html', 2010: 'index-20100208.html', 2011: 'index-20110212.html', + 2012: 'index-2012-03-09.html', + 2013: 'index-2013-03-07.html', } -- cgit v1.2.3-54-g00ecf