Merge pull request #5841 from rjsparks/related_no_alias
feat: Remove DocAlias from RelatedDocument
This commit is contained in:
commit
9f0b2b5432
|
@ -934,7 +934,7 @@ class RfcdiffSupportTests(TestCase):
|
|||
self.assertNotIn('previous', received, 'Rev 00 has no previous name when not replacing a draft')
|
||||
|
||||
replaced = IndividualDraftFactory()
|
||||
RelatedDocument.objects.create(relationship_id='replaces',source=draft,target=replaced.docalias.first())
|
||||
RelatedDocument.objects.create(relationship_id='replaces',source=draft,target=replaced)
|
||||
received = self.getJson(dict(name=draft.name, rev='00'))
|
||||
self.assertEqual(received['previous'], f'{replaced.name}-{replaced.rev}',
|
||||
'Rev 00 has a previous name when replacing a draft')
|
||||
|
@ -965,7 +965,7 @@ class RfcdiffSupportTests(TestCase):
|
|||
def do_rfc_test(self, draft_name):
|
||||
draft = WgDraftFactory(name=draft_name, create_revisions=range(0,2))
|
||||
rfc = WgRfcFactory(group=draft.group, rfc_number=self.next_rfc_number())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
draft.set_state(State.objects.get(type_id='draft',slug='rfc'))
|
||||
draft.set_state(State.objects.get(type_id='draft-iesg', slug='pub'))
|
||||
draft, rfc = reload_db_objects(draft, rfc)
|
||||
|
@ -1017,7 +1017,7 @@ class RfcdiffSupportTests(TestCase):
|
|||
def test_rfc_with_tombstone(self):
|
||||
draft = WgDraftFactory(create_revisions=range(0,2))
|
||||
rfc = WgRfcFactory(rfc_number=3261,group=draft.group)# See views_doc.HAS_TOMBSTONE
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
draft.set_state(State.objects.get(type_id='draft',slug='rfc'))
|
||||
draft.set_state(State.objects.get(type_id='draft-iesg', slug='pub'))
|
||||
draft = reload_db_objects(draft)
|
||||
|
@ -1029,7 +1029,7 @@ class RfcdiffSupportTests(TestCase):
|
|||
def do_rfc_with_broken_history_test(self, draft_name):
|
||||
draft = WgDraftFactory(rev='10', name=draft_name)
|
||||
rfc = WgRfcFactory(group=draft.group, rfc_number=self.next_rfc_number())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
draft.set_state(State.objects.get(type_id='draft',slug='rfc'))
|
||||
draft.set_state(State.objects.get(type_id='draft-iesg', slug='pub'))
|
||||
draft = reload_db_objects(draft)
|
||||
|
|
|
@ -344,7 +344,7 @@ def rfcdiff_latest_json(request, name, rev=None):
|
|||
response['previous'] = f'{draft.name}-{prev_rev}'
|
||||
response['previous_url'] = get_previous_url(draft.name, prev_rev)
|
||||
elif doc.type_id == "draft" and not found_rev and doc.relateddocument_set.filter(relationship_id="became_rfc").exists():
|
||||
rfc = doc.related_that_doc("became_rfc")[0].document
|
||||
rfc = doc.related_that_doc("became_rfc")[0]
|
||||
response['content_url'] = rfc.get_href()
|
||||
response['name']=rfc.name
|
||||
prev_rev = doc.rev
|
||||
|
@ -359,7 +359,7 @@ def rfcdiff_latest_json(request, name, rev=None):
|
|||
if doc.rev == '00':
|
||||
replaces_docs = (history.doc if condition=='historic version' else doc).related_that_doc('replaces')
|
||||
if replaces_docs:
|
||||
replaces = replaces_docs[0].document
|
||||
replaces = replaces_docs[0]
|
||||
response['previous'] = f'{replaces.name}-{replaces.rev}'
|
||||
response['previous_url'] = get_previous_url(replaces.name, replaces.rev)
|
||||
else:
|
||||
|
|
|
@ -43,6 +43,7 @@ class DocActionHolderInline(admin.TabularInline):
|
|||
|
||||
class RelatedDocumentInline(admin.TabularInline):
|
||||
model = RelatedDocument
|
||||
fk_name= 'source'
|
||||
def this(self, instance):
|
||||
return instance.source.canonical_name()
|
||||
readonly_fields = ['this', ]
|
||||
|
@ -125,7 +126,7 @@ admin.site.register(DocReminder, DocReminderAdmin)
|
|||
class RelatedDocumentAdmin(admin.ModelAdmin):
|
||||
list_display = ['source', 'target', 'relationship', ]
|
||||
list_filter = ['relationship', ]
|
||||
search_fields = ['source__name', 'target__name', 'target__docs__name', ]
|
||||
search_fields = ['source__name', 'target__name', ]
|
||||
raw_id_fields = ['source', 'target', ]
|
||||
admin.site.register(RelatedDocument, RelatedDocumentAdmin)
|
||||
|
||||
|
|
|
@ -83,13 +83,7 @@ class BaseDocumentFactory(factory.django.DjangoModelFactory):
|
|||
def relations(obj, create, extracted, **kwargs): # pylint: disable=no-self-argument
|
||||
if create and extracted:
|
||||
for (rel_id, doc) in extracted:
|
||||
if isinstance(doc, Document):
|
||||
docalias = doc.docalias.first()
|
||||
elif isinstance(doc, DocAlias):
|
||||
docalias = doc
|
||||
else:
|
||||
continue
|
||||
obj.relateddocument_set.create(relationship_id=rel_id, target=docalias)
|
||||
obj.relateddocument_set.create(relationship_id=rel_id, target=doc)
|
||||
|
||||
@factory.post_generation
|
||||
def create_revisions(obj, create, extracted, **kwargs): # pylint: disable=no-self-argument
|
||||
|
@ -244,7 +238,7 @@ class StatusChangeFactory(BaseDocumentFactory):
|
|||
for (rel, target) in extracted:
|
||||
obj.relateddocument_set.create(relationship_id=rel,target=target)
|
||||
else:
|
||||
obj.relateddocument_set.create(relationship_id='tobcp', target=WgRfcFactory().docalias.first())
|
||||
obj.relateddocument_set.create(relationship_id='tobcp', target=WgRfcFactory())
|
||||
|
||||
@factory.post_generation
|
||||
def states(obj, create, extracted, **kwargs):
|
||||
|
@ -271,9 +265,9 @@ class ConflictReviewFactory(BaseDocumentFactory):
|
|||
if not create:
|
||||
return
|
||||
if extracted:
|
||||
obj.relateddocument_set.create(relationship_id='conflrev',target=extracted.docalias.first())
|
||||
obj.relateddocument_set.create(relationship_id='conflrev',target=extracted)
|
||||
else:
|
||||
obj.relateddocument_set.create(relationship_id='conflrev',target=DocumentFactory(name=obj.name.replace('conflict-review-','draft-'),type_id='draft',group=Group.objects.get(type_id='individ')).docalias.first())
|
||||
obj.relateddocument_set.create(relationship_id='conflrev',target=DocumentFactory(name=obj.name.replace('conflict-review-','draft-'),type_id='draft',group=Group.objects.get(type_id='individ')))
|
||||
|
||||
|
||||
@factory.post_generation
|
||||
|
|
|
@ -8,7 +8,7 @@ from django import forms
|
|||
from django.core.exceptions import ObjectDoesNotExist, ValidationError
|
||||
from django.core.validators import validate_email
|
||||
|
||||
from ietf.doc.fields import SearchableDocAliasesField, SearchableDocAliasField
|
||||
from ietf.doc.fields import SearchableDocumentField, SearchableDocumentsField
|
||||
from ietf.doc.models import RelatedDocument, DocExtResource
|
||||
from ietf.iesg.models import TelechatDate
|
||||
from ietf.iesg.utils import telechat_page_count
|
||||
|
@ -134,11 +134,11 @@ class ActionHoldersForm(forms.Form):
|
|||
IESG_APPROVED_STATE_LIST = ("ann", "rfcqueue", "pub")
|
||||
|
||||
class AddDownrefForm(forms.Form):
|
||||
rfc = SearchableDocAliasField(
|
||||
rfc = SearchableDocumentField(
|
||||
label="Referenced RFC",
|
||||
help_text="The RFC that is approved for downref",
|
||||
required=True)
|
||||
drafts = SearchableDocAliasesField(
|
||||
drafts = SearchableDocumentsField(
|
||||
label="Internet-Drafts that makes the reference",
|
||||
help_text="The Internet-Drafts that approve the downref in their Last Call",
|
||||
required=True)
|
||||
|
@ -148,7 +148,7 @@ class AddDownrefForm(forms.Form):
|
|||
raise forms.ValidationError("Please provide a referenced RFC and a referencing Internet-Draft")
|
||||
|
||||
rfc = self.cleaned_data['rfc']
|
||||
if rfc.document.type_id != "rfc":
|
||||
if rfc.type_id != "rfc":
|
||||
raise forms.ValidationError("Cannot find the RFC: " + rfc.name)
|
||||
return rfc
|
||||
|
||||
|
@ -158,10 +158,10 @@ class AddDownrefForm(forms.Form):
|
|||
|
||||
v_err_names = []
|
||||
drafts = self.cleaned_data['drafts']
|
||||
for da in drafts:
|
||||
state = da.document.get_state("draft-iesg")
|
||||
for d in drafts:
|
||||
state = d.get_state("draft-iesg")
|
||||
if not state or state.slug not in IESG_APPROVED_STATE_LIST:
|
||||
v_err_names.append(da.name)
|
||||
v_err_names.append(d.name)
|
||||
if v_err_names:
|
||||
raise forms.ValidationError("Internet-Draft is not yet approved: " + ", ".join(v_err_names))
|
||||
return drafts
|
||||
|
@ -173,23 +173,23 @@ class AddDownrefForm(forms.Form):
|
|||
v_err_pairs = []
|
||||
rfc = self.cleaned_data['rfc']
|
||||
drafts = self.cleaned_data['drafts']
|
||||
for da in drafts:
|
||||
if RelatedDocument.objects.filter(source=da.document, target=rfc, relationship_id='downref-approval'):
|
||||
v_err_pairs.append(f"{da.name} --> RFC {rfc.document.rfc_number}")
|
||||
for d in drafts:
|
||||
if RelatedDocument.objects.filter(source=d, target=rfc, relationship_id='downref-approval'):
|
||||
v_err_pairs.append(f"{d.name} --> RFC {rfc.rfc_number}")
|
||||
if v_err_pairs:
|
||||
raise forms.ValidationError("Downref is already in the registry: " + ", ".join(v_err_pairs))
|
||||
|
||||
if 'save_downref_anyway' not in self.data:
|
||||
# this check is skipped if the save_downref_anyway button is used
|
||||
v_err_refnorm = ""
|
||||
for da in drafts:
|
||||
if not RelatedDocument.objects.filter(source=da.document, target=rfc, relationship_id='refnorm'):
|
||||
for d in drafts:
|
||||
if not RelatedDocument.objects.filter(source=d, target=rfc, relationship_id='refnorm'):
|
||||
if v_err_refnorm:
|
||||
v_err_refnorm = v_err_refnorm + " or " + da.name
|
||||
v_err_refnorm = v_err_refnorm + " or " + d.name
|
||||
else:
|
||||
v_err_refnorm = da.name
|
||||
v_err_refnorm = d.name
|
||||
if v_err_refnorm:
|
||||
v_err_refnorm_prefix = f"There does not seem to be a normative reference to RFC {rfc.document.rfc_number} by "
|
||||
v_err_refnorm_prefix = f"There does not seem to be a normative reference to RFC {rfc.rfc_number} by "
|
||||
raise forms.ValidationError(v_err_refnorm_prefix + v_err_refnorm)
|
||||
|
||||
|
||||
|
|
|
@ -54,7 +54,7 @@ def email_ad_approved_doc(request, doc, text):
|
|||
|
||||
def email_ad_approved_conflict_review(request, review, ok_to_publish):
|
||||
"""Email notification when AD approves a conflict review"""
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target.document
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target
|
||||
(to, cc) = gather_address_lists("ad_approved_conflict_review")
|
||||
frm = request.user.person.formatted_email()
|
||||
send_mail(request,
|
||||
|
|
|
@ -130,9 +130,8 @@ class Command(BaseCommand):
|
|||
for draft in interesting_drafts.distinct().iterator():
|
||||
# Omit drafts that became RFCs, unless they were published in the last DEFAULT_YEARS
|
||||
if draft.get_state_slug()=="rfc":
|
||||
rfc_alias = next(iter(draft.related_that_doc("became_rfc")), None)
|
||||
log.assertion("rfc_alias is not None")
|
||||
rfc = rfc_alias.document
|
||||
rfc = next(iter(draft.related_that_doc("became_rfc")), None)
|
||||
log.assertion("rfc is not None")
|
||||
if rfc.latest_event(type='published_rfc').time < show_since:
|
||||
continue
|
||||
|
||||
|
|
77
ietf/doc/migrations/0011_relate_no_aliases.py
Normal file
77
ietf/doc/migrations/0011_relate_no_aliases.py
Normal file
|
@ -0,0 +1,77 @@
|
|||
# Generated by Django 4.2.2 on 2023-06-16 13:40
|
||||
|
||||
from django.db import migrations
|
||||
import django.db.models.deletion
|
||||
from django.db.models import F, Subquery, OuterRef
|
||||
import ietf.utils.models
|
||||
|
||||
def forward(apps, schema_editor):
|
||||
RelatedDocument = apps.get_model("doc", "RelatedDocument")
|
||||
DocAlias = apps.get_model("doc", "DocAlias")
|
||||
subquery = Subquery(DocAlias.objects.filter(pk=OuterRef("deprecated_target")).values("docs")[:1])
|
||||
RelatedDocument.objects.annotate(firstdoc=subquery).update(target=F("firstdoc"))
|
||||
|
||||
def reverse(apps, schema_editor):
|
||||
pass
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
dependencies = [
|
||||
("doc", "0010_move_rfc_docaliases"),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='relateddocument',
|
||||
name='target',
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
db_index=False,
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to='doc.docalias',
|
||||
),
|
||||
),
|
||||
migrations.RenameField(
|
||||
model_name="relateddocument",
|
||||
old_name="target",
|
||||
new_name="deprecated_target"
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name='relateddocument',
|
||||
name='deprecated_target',
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
db_index=True,
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to='doc.docalias',
|
||||
),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name="relateddocument",
|
||||
name="target",
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
default=1, # A lie, but a convenient one - no relations point here.
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
related_name="targets_related",
|
||||
to="doc.document",
|
||||
db_index=False,
|
||||
),
|
||||
preserve_default=False,
|
||||
),
|
||||
migrations.RunPython(forward, reverse),
|
||||
migrations.AlterField(
|
||||
model_name="relateddocument",
|
||||
name="target",
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
related_name="targets_related",
|
||||
to="doc.document",
|
||||
db_index=True,
|
||||
),
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name="relateddocument",
|
||||
name="deprecated_target",
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to='doc.DocAlias',
|
||||
),
|
||||
),
|
||||
]
|
80
ietf/doc/migrations/0012_relate_hist_no_aliases.py
Normal file
80
ietf/doc/migrations/0012_relate_hist_no_aliases.py
Normal file
|
@ -0,0 +1,80 @@
|
|||
# Generated by Django 4.2.2 on 2023-06-16 13:40
|
||||
|
||||
from django.db import migrations
|
||||
import django.db.models.deletion
|
||||
from django.db.models import F, Subquery, OuterRef
|
||||
import ietf.utils.models
|
||||
|
||||
def forward(apps, schema_editor):
|
||||
RelatedDocHistory = apps.get_model("doc", "RelatedDocHistory")
|
||||
DocAlias = apps.get_model("doc", "DocAlias")
|
||||
subquery = Subquery(DocAlias.objects.filter(pk=OuterRef("deprecated_target")).values("docs")[:1])
|
||||
RelatedDocHistory.objects.annotate(firstdoc=subquery).update(target=F("firstdoc"))
|
||||
|
||||
def reverse(apps, schema_editor):
|
||||
pass
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
dependencies = [
|
||||
("doc", "0011_relate_no_aliases"),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='relateddochistory',
|
||||
name='target',
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
db_index=False,
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to='doc.docalias',
|
||||
related_name='reversely_related_document_history_set',
|
||||
),
|
||||
),
|
||||
migrations.RenameField(
|
||||
model_name="relateddochistory",
|
||||
old_name="target",
|
||||
new_name="deprecated_target"
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name='relateddochistory',
|
||||
name='deprecated_target',
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
db_index=True,
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to='doc.docalias',
|
||||
related_name='deprecated_reversely_related_document_history_set',
|
||||
),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name="relateddochistory",
|
||||
name="target",
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
default=1, # A lie, but a convenient one - no relations point here.
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to="doc.document",
|
||||
db_index=False,
|
||||
related_name='reversely_related_document_history_set',
|
||||
),
|
||||
preserve_default=False,
|
||||
),
|
||||
migrations.RunPython(forward, reverse),
|
||||
migrations.AlterField(
|
||||
model_name="relateddochistory",
|
||||
name="target",
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to="doc.document",
|
||||
db_index=True,
|
||||
related_name='reversely_related_document_history_set',
|
||||
),
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name="relateddochistory",
|
||||
name="deprecated_target",
|
||||
field=ietf.utils.models.ForeignKey(
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
to='doc.DocAlias',
|
||||
related_name='deprecated_reversely_related_document_history_set',
|
||||
),
|
||||
),
|
||||
]
|
|
@ -453,9 +453,9 @@ class DocumentInfo(models.Model):
|
|||
if not isinstance(relationship, tuple):
|
||||
raise TypeError("Expected a string or tuple, received %s" % type(relationship))
|
||||
if isinstance(self, Document):
|
||||
return RelatedDocument.objects.filter(target__docs=self, relationship__in=relationship).select_related('source')
|
||||
return RelatedDocument.objects.filter(target=self, relationship__in=relationship).select_related('source')
|
||||
elif isinstance(self, DocHistory):
|
||||
return RelatedDocHistory.objects.filter(target__docs=self.doc, relationship__in=relationship).select_related('source')
|
||||
return RelatedDocHistory.objects.filter(target=self.doc, relationship__in=relationship).select_related('source')
|
||||
else:
|
||||
raise TypeError("Expected method called on Document or DocHistory")
|
||||
|
||||
|
@ -489,8 +489,7 @@ class DocumentInfo(models.Model):
|
|||
for r in rels:
|
||||
if not r in related:
|
||||
related += ( r, )
|
||||
for doc in r.target.docs.all():
|
||||
related = doc.all_relations_that_doc(relationship, related)
|
||||
related = r.target.all_relations_that_doc(relationship, related)
|
||||
return related
|
||||
|
||||
def related_that(self, relationship):
|
||||
|
@ -663,7 +662,7 @@ STATUSCHANGE_RELATIONS = ('tops','tois','tohist','toinf','tobcp','toexp')
|
|||
|
||||
class RelatedDocument(models.Model):
|
||||
source = ForeignKey('Document')
|
||||
target = ForeignKey('DocAlias')
|
||||
target = ForeignKey('Document', related_name='targets_related')
|
||||
relationship = ForeignKey(DocRelationshipName)
|
||||
def action(self):
|
||||
return self.relationship.name
|
||||
|
@ -686,16 +685,16 @@ class RelatedDocument(models.Model):
|
|||
if source_lvl not in ['bcp','ps','ds','std']:
|
||||
return None
|
||||
|
||||
if self.target.document.type_id == 'rfc':
|
||||
if not self.target.document.std_level:
|
||||
if self.target.type_id == 'rfc':
|
||||
if not self.target.std_level:
|
||||
target_lvl = 'unkn'
|
||||
else:
|
||||
target_lvl = self.target.document.std_level.slug
|
||||
target_lvl = self.target.std_level.slug
|
||||
else:
|
||||
if not self.target.document.intended_std_level:
|
||||
if not self.target.intended_std_level:
|
||||
target_lvl = 'unkn'
|
||||
else:
|
||||
target_lvl = self.target.document.intended_std_level.slug
|
||||
target_lvl = self.target.intended_std_level.slug
|
||||
|
||||
rank = { 'ps':1, 'ds':2, 'std':3, 'bcp':3 }
|
||||
|
||||
|
@ -709,7 +708,7 @@ class RelatedDocument(models.Model):
|
|||
|
||||
def is_approved_downref(self):
|
||||
|
||||
if self.target.document.type_id == "rfc":
|
||||
if self.target.type_id == 'rfc':
|
||||
if RelatedDocument.objects.filter(relationship_id='downref-approval', target=self.target).exists():
|
||||
return "Approved Downref"
|
||||
|
||||
|
@ -962,7 +961,15 @@ class Document(DocumentInfo):
|
|||
document directly or indirectly obsoletes or replaces
|
||||
"""
|
||||
from ietf.ipr.models import IprDocRel
|
||||
iprs = IprDocRel.objects.filter(document__in=list(self.docalias.all())+self.all_related_that_doc(('obs','replaces'))).filter(disclosure__state__in=('posted','removed')).values_list('disclosure', flat=True).distinct()
|
||||
iprs = (
|
||||
IprDocRel.objects.filter(
|
||||
document__in=list(self.docalias.all())
|
||||
+ [x.docalias.first() for x in self.all_related_that_doc(("obs", "replaces"))] # this really is docalias until IprDocRel changes
|
||||
)
|
||||
.filter(disclosure__state__in=("posted", "removed"))
|
||||
.values_list("disclosure", flat=True)
|
||||
.distinct()
|
||||
)
|
||||
return iprs
|
||||
|
||||
def future_presentations(self):
|
||||
|
@ -1101,7 +1108,7 @@ class DocExtResource(ExtResource):
|
|||
|
||||
class RelatedDocHistory(models.Model):
|
||||
source = ForeignKey('DocHistory')
|
||||
target = ForeignKey('DocAlias', related_name="reversely_related_document_history_set")
|
||||
target = ForeignKey('Document', related_name="reversely_related_document_history_set")
|
||||
relationship = ForeignKey(DocRelationshipName)
|
||||
def __str__(self):
|
||||
return u"%s %s %s" % (self.source.doc.name, self.relationship.name.lower(), self.target.name)
|
||||
|
|
|
@ -288,8 +288,8 @@ def urlize_related_target_list(related, document_html=False):
|
|||
"""Convert a list of RelatedDocuments into list of links using the target document's canonical name"""
|
||||
links = []
|
||||
for rel in related:
|
||||
name=rel.target.document.canonical_name()
|
||||
title = rel.target.document.title
|
||||
name=rel.target.canonical_name()
|
||||
title = rel.target.title
|
||||
url = urlreverse('ietf.doc.views_doc.document_main' if document_html is False else 'ietf.doc.views_doc.document_html', kwargs=dict(name=name))
|
||||
name = escape(name)
|
||||
title = escape(title)
|
||||
|
|
|
@ -624,7 +624,15 @@ Man Expires September 22, 2015 [Page 3]
|
|||
# Docs for testing relationships. Does not test 'possibly-replaces'. The 'replaced_by' direction
|
||||
# is tested separately below.
|
||||
replaced = IndividualDraftFactory()
|
||||
draft.relateddocument_set.create(relationship_id='replaces',source=draft,target=replaced.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id='replaces',source=draft,target=replaced)
|
||||
obsoleted = IndividualDraftFactory()
|
||||
draft.relateddocument_set.create(relationship_id='obs',source=draft,target=obsoleted)
|
||||
obsoleted_by = IndividualDraftFactory()
|
||||
obsoleted_by.relateddocument_set.create(relationship_id='obs',source=obsoleted_by,target=draft)
|
||||
updated = IndividualDraftFactory()
|
||||
draft.relateddocument_set.create(relationship_id='updates',source=draft,target=updated)
|
||||
updated_by = IndividualDraftFactory()
|
||||
updated_by.relateddocument_set.create(relationship_id='updates',source=obsoleted_by,target=draft)
|
||||
|
||||
DocExtResourceFactory(doc=draft)
|
||||
|
||||
|
@ -746,7 +754,7 @@ Man Expires September 22, 2015 [Page 3]
|
|||
shepherd_id=draft.shepherd_id, ad_id=draft.ad_id, expires=draft.expires,
|
||||
notify=draft.notify, note=draft.note)
|
||||
rel = RelatedDocument.objects.create(source=replacement,
|
||||
target=draft.docalias.get(name__startswith="draft"),
|
||||
target=draft,
|
||||
relationship_id="replaces")
|
||||
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_main", kwargs=dict(name=draft.name)))
|
||||
|
@ -763,16 +771,16 @@ Man Expires September 22, 2015 [Page 3]
|
|||
rfc = WgRfcFactory(group=draft.group, name="rfc123456")
|
||||
rfc.save_with_history([DocEvent.objects.create(doc=rfc, rev=None, type="published_rfc", by=Person.objects.get(name="(System)"))])
|
||||
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
|
||||
obsoleted = IndividualRfcFactory()
|
||||
rfc.relateddocument_set.create(relationship_id='obs',target=obsoleted.docalias.first())
|
||||
rfc.relateddocument_set.create(relationship_id='obs',target=obsoleted)
|
||||
obsoleted_by = IndividualRfcFactory()
|
||||
obsoleted_by.relateddocument_set.create(relationship_id='obs',target=rfc.docalias.first())
|
||||
obsoleted_by.relateddocument_set.create(relationship_id='obs',target=rfc)
|
||||
updated = IndividualRfcFactory()
|
||||
rfc.relateddocument_set.create(relationship_id='updates',target=updated.docalias.first())
|
||||
rfc.relateddocument_set.create(relationship_id='updates',target=updated)
|
||||
updated_by = IndividualRfcFactory()
|
||||
updated_by.relateddocument_set.create(relationship_id='updates',target=rfc.docalias.first())
|
||||
updated_by.relateddocument_set.create(relationship_id='updates',target=rfc)
|
||||
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_main", kwargs=dict(name=draft.name)))
|
||||
self.assertEqual(r.status_code, 302)
|
||||
|
@ -821,7 +829,7 @@ Man Expires September 22, 2015 [Page 3]
|
|||
draft = WgRfcFactory()
|
||||
status_change_doc = StatusChangeFactory(
|
||||
group=draft.group,
|
||||
changes_status_of=[('tops', draft.docalias.first())],
|
||||
changes_status_of=[('tops', draft)],
|
||||
)
|
||||
status_change_url = urlreverse(
|
||||
'ietf.doc.views_doc.document_main',
|
||||
|
@ -829,7 +837,7 @@ Man Expires September 22, 2015 [Page 3]
|
|||
)
|
||||
proposed_status_change_doc = StatusChangeFactory(
|
||||
group=draft.group,
|
||||
changes_status_of=[('tobcp', draft.docalias.first())],
|
||||
changes_status_of=[('tobcp', draft)],
|
||||
states=[State.objects.get(slug='needshep', type='statchg')],
|
||||
)
|
||||
proposed_status_change_url = urlreverse(
|
||||
|
@ -1422,7 +1430,7 @@ Man Expires September 22, 2015 [Page 3]
|
|||
|
||||
rfc = WgRfcFactory(group=group)
|
||||
draft = WgDraftFactory(group=group)
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
DocEventFactory.create(doc=rfc, type='published_rfc', time=event_datetime)
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_main", kwargs=dict(name=rfc.name)))
|
||||
self.assertEqual(r.status_code, 200)
|
||||
|
@ -1437,7 +1445,7 @@ Man Expires September 22, 2015 [Page 3]
|
|||
|
||||
rfc = WgRfcFactory(group=group)
|
||||
draft = WgDraftFactory(name='draft-rfc-document-%s'% group_type_id, group=group)
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
DocEventFactory.create(doc=rfc, type='published_rfc', time=event_datetime)
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_main", kwargs=dict(name=rfc.name)))
|
||||
self.assertEqual(r.status_code, 200)
|
||||
|
@ -1540,7 +1548,7 @@ class DocTestCase(TestCase):
|
|||
statchg = StatusChangeFactory()
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_main", kwargs=dict(name=statchg.name)))
|
||||
self.assertEqual(r.status_code, 200)
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_main", kwargs=dict(name=statchg.relateddocument_set.first().target.document.name)))
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_main", kwargs=dict(name=statchg.relateddocument_set.first().target)))
|
||||
self.assertEqual(r.status_code, 200)
|
||||
|
||||
def test_document_charter(self):
|
||||
|
@ -1701,8 +1709,8 @@ class DocTestCase(TestCase):
|
|||
self.assertNotContains(r, 'more YES or NO')
|
||||
|
||||
# status change
|
||||
DocAlias.objects.create(name='rfc9998').docs.add(IndividualDraftFactory())
|
||||
DocAlias.objects.create(name='rfc9999').docs.add(IndividualDraftFactory())
|
||||
Document.objects.create(name='rfc9998')
|
||||
Document.objects.create(name='rfc9999')
|
||||
doc = DocumentFactory(type_id='statchg',name='status-change-imaginary-mid-review')
|
||||
iesgeval_pk = str(State.objects.get(slug='iesgeval',type__slug='statchg').pk)
|
||||
empty_outbox()
|
||||
|
@ -1715,12 +1723,12 @@ class DocTestCase(TestCase):
|
|||
self.assertIn('iesg-secretary',outbox[0]['To'])
|
||||
self.assertIn('drafts-eval',outbox[1]['To'])
|
||||
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_ballot", kwargs=dict(name=doc.name)))
|
||||
self.assertNotContains(r, 'Needs a YES')
|
||||
self.assertNotContains(r, 'more YES or NO')
|
||||
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
r = self.client.get(urlreverse("ietf.doc.views_doc.document_ballot", kwargs=dict(name=doc.name)))
|
||||
self.assertContains(r, 'more YES or NO')
|
||||
|
||||
|
@ -2037,7 +2045,7 @@ class ReferencesTest(TestCase):
|
|||
|
||||
def test_references(self):
|
||||
doc1 = WgDraftFactory(name='draft-ietf-mars-test')
|
||||
doc2 = IndividualDraftFactory(name='draft-imaginary-independent-submission').docalias.first()
|
||||
doc2 = IndividualDraftFactory(name='draft-imaginary-independent-submission')
|
||||
RelatedDocument.objects.get_or_create(source=doc1,target=doc2,relationship=DocRelationshipName.objects.get(slug='refnorm'))
|
||||
url = urlreverse('ietf.doc.views_doc.document_references', kwargs=dict(name=doc1.name))
|
||||
r = self.client.get(url)
|
||||
|
@ -2103,7 +2111,7 @@ class GenerateDraftAliasesTests(TestCase):
|
|||
rfc3 = WgRfcFactory()
|
||||
DocEventFactory.create(doc=rfc3, type="published_rfc", time=a_month_ago)
|
||||
doc3.relateddocument_set.create(
|
||||
relationship_id="became_rfc", target=rfc3.docalias.first()
|
||||
relationship_id="became_rfc", target=rfc3
|
||||
)
|
||||
doc4 = WgDraftFactory.create(
|
||||
authors=[author4, author5],
|
||||
|
@ -2119,7 +2127,7 @@ class GenerateDraftAliasesTests(TestCase):
|
|||
time=datetime.datetime(2010, 10, 10, tzinfo=RPC_TZINFO),
|
||||
)
|
||||
doc4.relateddocument_set.create(
|
||||
relationship_id="became_rfc", target=rfc4.docalias.first()
|
||||
relationship_id="became_rfc", target=rfc4
|
||||
)
|
||||
doc5 = IndividualDraftFactory(authors=[author6])
|
||||
|
||||
|
@ -2673,7 +2681,7 @@ class Idnits2SupportTests(TestCase):
|
|||
def test_idnits2_state(self):
|
||||
rfc = WgRfcFactory()
|
||||
draft = WgDraftFactory()
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
url = urlreverse('ietf.doc.views_doc.idnits2_state', kwargs=dict(name=rfc.canonical_name()))
|
||||
r = self.client.get(url)
|
||||
self.assertEqual(r.status_code, 200)
|
||||
|
@ -2760,7 +2768,7 @@ class PdfizedTests(TestCase):
|
|||
def test_pdfized(self):
|
||||
rfc = WgRfcFactory()
|
||||
draft = WgDraftFactory(create_revisions=range(0,2))
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
|
||||
dir = settings.RFC_PATH
|
||||
with (Path(dir) / f'{rfc.name}.txt').open('w') as f:
|
||||
|
|
|
@ -803,8 +803,8 @@ class ApproveBallotTests(TestCase):
|
|||
desc='Last call announcement was changed',
|
||||
text='this is simple last call text.' )
|
||||
rfc = IndividualRfcFactory.create(
|
||||
name = "rfc6666",
|
||||
stream_id='ise',
|
||||
other_aliases=['rfc6666',],
|
||||
states=[('draft','rfc'),('draft-iesg','pub')],
|
||||
std_level_id='inf', )
|
||||
|
||||
|
@ -821,7 +821,7 @@ class ApproveBallotTests(TestCase):
|
|||
self.assertContains(r, "No downward references for")
|
||||
|
||||
# Add a downref, the page should ask if it should be added to the registry
|
||||
rel = draft.relateddocument_set.create(target=rfc.docalias.get(name='rfc6666'),relationship_id='refnorm')
|
||||
rel = draft.relateddocument_set.create(target=rfc, relationship_id='refnorm')
|
||||
d = [rdoc for rdoc in draft.relateddocument_set.all() if rel.is_approved_downref()]
|
||||
original_len = len(d)
|
||||
r = self.client.get(url)
|
||||
|
@ -1127,7 +1127,7 @@ class RegenerateLastCallTestCase(TestCase):
|
|||
std_level_id='inf',
|
||||
)
|
||||
|
||||
draft.relateddocument_set.create(target=rfc.docalias.get(name='rfc6666'),relationship_id='refnorm')
|
||||
draft.relateddocument_set.create(target=rfc,relationship_id='refnorm')
|
||||
|
||||
r = self.client.post(url, dict(regenerate_last_call_text="1"))
|
||||
self.assertEqual(r.status_code, 200)
|
||||
|
@ -1137,7 +1137,7 @@ class RegenerateLastCallTestCase(TestCase):
|
|||
self.assertTrue("rfc6666" in lc_text)
|
||||
self.assertTrue("Independent Submission" in lc_text)
|
||||
|
||||
draft.relateddocument_set.create(target=rfc.docalias.get(name='rfc6666'), relationship_id='downref-approval')
|
||||
draft.relateddocument_set.create(target=rfc, relationship_id='downref-approval')
|
||||
|
||||
r = self.client.post(url, dict(regenerate_last_call_text="1"))
|
||||
self.assertEqual(r.status_code, 200)
|
||||
|
|
|
@ -70,12 +70,12 @@ class ConflictReviewTests(TestCase):
|
|||
self.assertEqual(review_doc.ad.name,'Areað Irector')
|
||||
self.assertEqual(review_doc.notify,'ipu@ietf.org')
|
||||
doc = Document.objects.get(name='draft-imaginary-independent-submission')
|
||||
self.assertTrue(doc in [x.target.document for x in review_doc.relateddocument_set.filter(relationship__slug='conflrev')])
|
||||
self.assertTrue(doc in [x.target for x in review_doc.relateddocument_set.filter(relationship__slug='conflrev')])
|
||||
|
||||
self.assertTrue(review_doc.latest_event(DocEvent,type="added_comment").desc.startswith("IETF conflict review requested"))
|
||||
self.assertTrue(doc.latest_event(DocEvent,type="added_comment").desc.startswith("IETF conflict review initiated"))
|
||||
self.assertTrue('Conflict Review requested' in outbox[-1]['Subject'])
|
||||
|
||||
|
||||
# verify you can't start a review when a review is already in progress
|
||||
r = self.client.post(url,dict(ad="Areað Irector",create_in_state="Needs Shepherd",notify='ipu@ietf.org'))
|
||||
self.assertEqual(r.status_code, 404)
|
||||
|
@ -119,7 +119,7 @@ class ConflictReviewTests(TestCase):
|
|||
self.assertEqual(review_doc.ad.name,'Ietf Chair')
|
||||
self.assertEqual(review_doc.notify,'ipu@ietf.org')
|
||||
doc = Document.objects.get(name='draft-imaginary-independent-submission')
|
||||
self.assertTrue(doc in [x.target.document for x in review_doc.relateddocument_set.filter(relationship__slug='conflrev')])
|
||||
self.assertTrue(doc in [x.target for x in review_doc.relateddocument_set.filter(relationship__slug='conflrev')])
|
||||
|
||||
self.assertEqual(len(outbox), messages_before + 2)
|
||||
|
||||
|
|
|
@ -24,7 +24,7 @@ class Downref(TestCase):
|
|||
self.docalias = self.doc.docalias.get(name='draft-ietf-mars-approved-document')
|
||||
self.rfc = WgRfcFactory(rfc_number=9998)
|
||||
self.rfcalias = self.rfc.docalias.get(name='rfc9998')
|
||||
RelatedDocument.objects.create(source=self.doc, target=self.rfcalias, relationship_id='downref-approval')
|
||||
RelatedDocument.objects.create(source=self.doc, target=self.rfc, relationship_id='downref-approval')
|
||||
|
||||
def test_downref_registry(self):
|
||||
url = urlreverse('ietf.doc.views_downref.downref_registry')
|
||||
|
@ -64,36 +64,36 @@ class Downref(TestCase):
|
|||
self.assertContains(r, 'Save downref')
|
||||
|
||||
# error - already in the downref registry
|
||||
r = self.client.post(url, dict(rfc=self.rfcalias.pk, drafts=(self.docalias.pk, )))
|
||||
r = self.client.post(url, dict(rfc=self.rfc.pk, drafts=(self.doc.pk, )))
|
||||
self.assertContains(r, 'Downref is already in the registry')
|
||||
|
||||
# error - source is not in an approved state
|
||||
r = self.client.get(url)
|
||||
self.assertEqual(r.status_code, 200)
|
||||
r = self.client.post(url, dict(rfc=self.rfcalias.pk, drafts=(self.draftalias.pk, )))
|
||||
r = self.client.post(url, dict(rfc=self.rfc.pk, drafts=(self.draft.pk, )))
|
||||
self.assertContains(r, 'Draft is not yet approved')
|
||||
|
||||
# error - the target is not a normative reference of the source
|
||||
self.draft.set_state(State.objects.get(used=True, type="draft-iesg", slug="pub"))
|
||||
r = self.client.get(url)
|
||||
self.assertEqual(r.status_code, 200)
|
||||
r = self.client.post(url, dict(rfc=self.rfcalias.pk, drafts=(self.draftalias.pk, )))
|
||||
r = self.client.post(url, dict(rfc=self.rfc.pk, drafts=(self.draft.pk, )))
|
||||
self.assertContains(r, 'There does not seem to be a normative reference to RFC')
|
||||
self.assertContains(r, 'Save downref anyway')
|
||||
|
||||
# normal - approve the document so the downref is now okay
|
||||
RelatedDocument.objects.create(source=self.draft, target=self.rfcalias, relationship_id='refnorm')
|
||||
RelatedDocument.objects.create(source=self.draft, target=self.rfc, relationship_id='refnorm')
|
||||
draft_de_count_before = self.draft.docevent_set.count()
|
||||
rfc_de_count_before = self.rfc.docevent_set.count()
|
||||
|
||||
r = self.client.get(url)
|
||||
self.assertEqual(r.status_code, 200)
|
||||
r = self.client.post(url, dict(rfc=self.rfcalias.pk, drafts=(self.draftalias.pk, )))
|
||||
r = self.client.post(url, dict(rfc=self.rfc.pk, drafts=(self.draft.pk, )))
|
||||
self.assertEqual(r.status_code, 302)
|
||||
newurl = urlreverse('ietf.doc.views_downref.downref_registry')
|
||||
r = self.client.get(newurl)
|
||||
self.assertContains(r, '<a href="/doc/draft-ietf-mars-test')
|
||||
self.assertTrue(RelatedDocument.objects.filter(source=self.draft, target=self.rfcalias, relationship_id='downref-approval'))
|
||||
self.assertTrue(RelatedDocument.objects.filter(source=self.draft, target=self.rfc, relationship_id='downref-approval'))
|
||||
self.assertEqual(self.draft.docevent_set.count(), draft_de_count_before + 1)
|
||||
self.assertEqual(self.rfc.docevent_set.count(), rfc_de_count_before + 1)
|
||||
|
||||
|
@ -101,7 +101,7 @@ class Downref(TestCase):
|
|||
draft = WgDraftFactory(name='draft-ietf-mars-ready-for-lc-document',intended_std_level_id='ps',states=[('draft-iesg','iesg-eva')])
|
||||
WgDraftFactory(name='draft-ietf-mars-another-approved-document',states=[('draft-iesg','rfcqueue')])
|
||||
rfc9999 = WgRfcFactory(rfc_number=9999, std_level_id=None)
|
||||
RelatedDocument.objects.create(source=draft, target=rfc9999.docalias.get(name='rfc9999'), relationship_id='refnorm')
|
||||
RelatedDocument.objects.create(source=draft, target=rfc9999, relationship_id='refnorm')
|
||||
url = urlreverse('ietf.doc.views_ballot.lastcalltext', kwargs=dict(name=draft.name))
|
||||
login_testing_unauthorized(self, "secretary", url)
|
||||
|
||||
|
@ -113,7 +113,7 @@ class Downref(TestCase):
|
|||
self.assertIn('The document contains these normative downward references', text)
|
||||
|
||||
# now, the announcement text about the downref to RFC 9999 should be gone
|
||||
RelatedDocument.objects.create(source=draft, target=rfc9999.docalias.get(name='rfc9999'),relationship_id='downref-approval')
|
||||
RelatedDocument.objects.create(source=draft, target=rfc9999, relationship_id='downref-approval')
|
||||
r = self.client.post(url, dict(regenerate_last_call_text="1"))
|
||||
self.assertEqual(r.status_code, 200)
|
||||
q = PyQuery(r.content)
|
||||
|
|
|
@ -2017,10 +2017,10 @@ class ChangeReplacesTests(TestCase):
|
|||
|
||||
# Post that says replacea replaces base a
|
||||
empty_outbox()
|
||||
RelatedDocument.objects.create(source=self.replacea, target=self.basea.docalias.first(),
|
||||
RelatedDocument.objects.create(source=self.replacea, target=self.basea,
|
||||
relationship=DocRelationshipName.objects.get(slug="possibly-replaces"))
|
||||
self.assertEqual(self.basea.get_state().slug,'active')
|
||||
r = self.client.post(url, dict(replaces=self.basea.docalias.first().pk))
|
||||
r = self.client.post(url, dict(replaces=self.basea.pk))
|
||||
self.assertEqual(r.status_code, 302)
|
||||
self.assertEqual(RelatedDocument.objects.filter(relationship__slug='replaces',source=self.replacea).count(),1)
|
||||
self.assertEqual(Document.objects.get(name='draft-test-base-a').get_state().slug,'repl')
|
||||
|
@ -2034,7 +2034,7 @@ class ChangeReplacesTests(TestCase):
|
|||
# Post that says replaceboth replaces both base a and base b
|
||||
url = urlreverse('ietf.doc.views_draft.replaces', kwargs=dict(name=self.replaceboth.name))
|
||||
self.assertEqual(self.baseb.get_state().slug,'expired')
|
||||
r = self.client.post(url, dict(replaces=[self.basea.docalias.first().pk, self.baseb.docalias.first().pk]))
|
||||
r = self.client.post(url, dict(replaces=[self.basea.pk, self.baseb.pk]))
|
||||
self.assertEqual(r.status_code, 302)
|
||||
self.assertEqual(Document.objects.get(name='draft-test-base-a').get_state().slug,'repl')
|
||||
self.assertEqual(Document.objects.get(name='draft-test-base-b').get_state().slug,'repl')
|
||||
|
@ -2065,7 +2065,7 @@ class ChangeReplacesTests(TestCase):
|
|||
|
||||
|
||||
def test_review_possibly_replaces(self):
|
||||
replaced = self.basea.docalias.first()
|
||||
replaced = self.basea
|
||||
RelatedDocument.objects.create(source=self.replacea, target=replaced,
|
||||
relationship=DocRelationshipName.objects.get(slug="possibly-replaces"))
|
||||
|
||||
|
@ -2093,7 +2093,7 @@ class MoreReplacesTests(TestCase):
|
|||
new_doc = IndividualDraftFactory(stream_id=stream)
|
||||
|
||||
url = urlreverse('ietf.doc.views_draft.replaces', kwargs=dict(name=new_doc.name))
|
||||
r = self.client.post(url, dict(replaces=old_doc.docalias.first().pk))
|
||||
r = self.client.post(url, dict(replaces=old_doc.pk))
|
||||
self.assertEqual(r.status_code,302)
|
||||
old_doc = Document.objects.get(name=old_doc.name)
|
||||
self.assertEqual(old_doc.get_state_slug('draft'),'repl')
|
||||
|
|
|
@ -161,8 +161,8 @@ class ReviewTests(TestCase):
|
|||
# check we can fish it out
|
||||
old_doc = WgDraftFactory(name="draft-foo-mars-test")
|
||||
older_doc = WgDraftFactory(name="draft-older")
|
||||
RelatedDocument.objects.create(source=old_doc, target=older_doc.docalias.first(), relationship_id='replaces')
|
||||
RelatedDocument.objects.create(source=doc, target=old_doc.docalias.first(), relationship_id='replaces')
|
||||
RelatedDocument.objects.create(source=old_doc, target=older_doc, relationship_id='replaces')
|
||||
RelatedDocument.objects.create(source=doc, target=old_doc, relationship_id='replaces')
|
||||
review_req.doc = older_doc
|
||||
review_req.save()
|
||||
|
||||
|
|
|
@ -15,7 +15,7 @@ from django.conf import settings
|
|||
from django.urls import reverse as urlreverse
|
||||
|
||||
from ietf.doc.factories import DocumentFactory, IndividualRfcFactory, WgRfcFactory, WgDraftFactory
|
||||
from ietf.doc.models import ( Document, DocAlias, State, DocEvent,
|
||||
from ietf.doc.models import ( Document, State, DocEvent,
|
||||
BallotPositionDocEvent, NewRevisionDocEvent, TelechatDocEvent, WriteupDocEvent )
|
||||
from ietf.doc.utils import create_ballot_if_not_open
|
||||
from ietf.doc.views_status_change import default_approval_text
|
||||
|
@ -74,7 +74,7 @@ class StatusChangeTests(TestCase):
|
|||
self.assertEqual(status_change.rev,'00')
|
||||
self.assertEqual(status_change.ad.name,'Areað Irector')
|
||||
self.assertEqual(status_change.notify,'ipu@ietf.org')
|
||||
self.assertTrue(status_change.relateddocument_set.filter(relationship__slug='tois',target__docs__name='rfc9999'))
|
||||
self.assertTrue(status_change.relateddocument_set.filter(relationship__slug='tois',target__name='rfc9999'))
|
||||
|
||||
# Verify that it's possible to start a status change without a responsible ad.
|
||||
r = self.client.post(url,dict(
|
||||
|
@ -159,8 +159,8 @@ class StatusChangeTests(TestCase):
|
|||
self.assertTrue(doc.latest_event(DocEvent,type="added_comment").desc.startswith('Notification list changed'))
|
||||
|
||||
# Some additional setup so there's something to put in a generated notify list
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
|
||||
# Ask the form to regenerate the list
|
||||
r = self.client.post(url,dict(regenerate_addresses="1"))
|
||||
|
@ -263,8 +263,8 @@ class StatusChangeTests(TestCase):
|
|||
login_testing_unauthorized(self, "ad", url)
|
||||
|
||||
# additional setup
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
doc.ad = Person.objects.get(name='Ad No2')
|
||||
doc.save_with_history([DocEvent.objects.create(doc=doc, rev=doc.rev, type="changed_document", by=Person.objects.get(user__username="secretary"), desc="Test")])
|
||||
|
||||
|
@ -307,8 +307,8 @@ class StatusChangeTests(TestCase):
|
|||
login_testing_unauthorized(self, "secretary", url)
|
||||
|
||||
# Some additional setup
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
create_ballot_if_not_open(None, doc, Person.objects.get(user__username="secretary"), "statchg")
|
||||
doc.set_state(State.objects.get(slug='appr-pend',type='statchg'))
|
||||
|
||||
|
@ -348,10 +348,10 @@ class StatusChangeTests(TestCase):
|
|||
url = urlreverse('ietf.doc.views_status_change.change_state',kwargs=dict(name=doc.name))
|
||||
|
||||
# Add some status change related documents
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
# And a non-status change related document
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc14'),relationship_id='updates')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc14'),relationship_id='updates')
|
||||
|
||||
login_testing_unauthorized(self, role, url)
|
||||
empty_outbox()
|
||||
|
@ -373,9 +373,9 @@ class StatusChangeTests(TestCase):
|
|||
self.assertTrue(notification['Subject'].startswith('Approved:'))
|
||||
notification_text = get_payload_text(notification)
|
||||
self.assertIn('The AD has approved changing the status', notification_text)
|
||||
self.assertIn(DocAlias.objects.get(name='rfc9999').document.canonical_name(), notification_text)
|
||||
self.assertIn(DocAlias.objects.get(name='rfc9998').document.canonical_name(), notification_text)
|
||||
self.assertNotIn(DocAlias.objects.get(name='rfc14').document.canonical_name(), notification_text)
|
||||
self.assertIn(Document.objects.get(name='rfc9999').canonical_name(), notification_text)
|
||||
self.assertIn(Document.objects.get(name='rfc9998').canonical_name(), notification_text)
|
||||
self.assertNotIn(Document.objects.get(name='rfc14').canonical_name(), notification_text)
|
||||
self.assertNotIn('No value found for', notification_text) # make sure all interpolation values were set
|
||||
else:
|
||||
self.assertEqual(len(outbox), 0)
|
||||
|
@ -395,8 +395,8 @@ class StatusChangeTests(TestCase):
|
|||
login_testing_unauthorized(self, "secretary", url)
|
||||
|
||||
# Some additional setup
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=DocAlias.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9999'),relationship_id='tois')
|
||||
doc.relateddocument_set.create(target=Document.objects.get(name='rfc9998'),relationship_id='tohist')
|
||||
|
||||
# get
|
||||
r = self.client.get(url)
|
||||
|
@ -453,11 +453,11 @@ class StatusChangeTests(TestCase):
|
|||
|
||||
rfc = WgRfcFactory(rfc_number=9999,std_level_id='ps')
|
||||
draft = WgDraftFactory(name='draft-ietf-random-thing')
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
|
||||
rfc = WgRfcFactory(rfc_number=9998,std_level_id='inf')
|
||||
draft = WgDraftFactory(name='draft-ietf-random-other-thing')
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
|
||||
DocumentFactory(type_id='statchg',name='status-change-imaginary-mid-review',notify='notify@example.org')
|
||||
|
||||
|
|
|
@ -253,7 +253,7 @@ class MiscTests(TestCase):
|
|||
def do_fuzzy_find_documents_rfc_test(self, name):
|
||||
draft = WgDraftFactory(name=name, create_revisions=(0, 1, 2))
|
||||
rfc = WgRfcFactory()
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
draft, rfc = reload_db_objects(draft, rfc)
|
||||
|
||||
# by canonical name
|
||||
|
@ -327,14 +327,14 @@ class RebuildReferenceRelationsTests(TestCase):
|
|||
super().setUp()
|
||||
self.doc = WgDraftFactory() # document under test
|
||||
# Other documents that should be found by rebuild_reference_relations
|
||||
self.normative, self.informative, self.unknown = WgRfcFactory.create_batch(3)
|
||||
self.normative, self.informative, self.unknown = WgRfcFactory.create_batch(3) # AMHERE - these need to have rfc names.
|
||||
for relationship in ['refnorm', 'refinfo', 'refunk', 'refold']:
|
||||
self.doc.relateddocument_set.create(
|
||||
target=WgRfcFactory().docalias.first(),
|
||||
target=WgRfcFactory(),
|
||||
relationship_id=relationship,
|
||||
)
|
||||
self.updated = WgRfcFactory() # related document that should be left alone
|
||||
self.doc.relateddocument_set.create(target=self.updated.docalias.first(), relationship_id='updates')
|
||||
self.doc.relateddocument_set.create(target=self.updated, relationship_id='updates')
|
||||
self.assertCountEqual(self.doc.relateddocument_set.values_list('relationship__slug', flat=True),
|
||||
['refnorm', 'refinfo', 'refold', 'refunk', 'updates'],
|
||||
'Test conditions set up incorrectly: wrong prior document relationships')
|
||||
|
@ -380,7 +380,7 @@ class RebuildReferenceRelationsTests(TestCase):
|
|||
self.assertEqual(
|
||||
result,
|
||||
{
|
||||
'warnings': ['There were 1 references with no matching DocAlias'],
|
||||
'warnings': ['There were 1 references with no matching Document'],
|
||||
'unfound': ['draft-not-found'],
|
||||
}
|
||||
)
|
||||
|
@ -391,7 +391,7 @@ class RebuildReferenceRelationsTests(TestCase):
|
|||
(self.normative.canonical_name(), 'refnorm'),
|
||||
(self.informative.canonical_name(), 'refinfo'),
|
||||
(self.unknown.canonical_name(), 'refunk'),
|
||||
(self.updated.docalias.first().name, 'updates'),
|
||||
(self.updated.name, 'updates'),
|
||||
]
|
||||
)
|
||||
|
||||
|
@ -411,7 +411,7 @@ class RebuildReferenceRelationsTests(TestCase):
|
|||
self.assertEqual(
|
||||
result,
|
||||
{
|
||||
'warnings': ['There were 1 references with no matching DocAlias'],
|
||||
'warnings': ['There were 1 references with no matching Document'],
|
||||
'unfound': ['draft-not-found'],
|
||||
}
|
||||
)
|
||||
|
@ -422,7 +422,7 @@ class RebuildReferenceRelationsTests(TestCase):
|
|||
(self.normative.canonical_name(), 'refnorm'),
|
||||
(self.informative.canonical_name(), 'refinfo'),
|
||||
(self.unknown.canonical_name(), 'refunk'),
|
||||
(self.updated.docalias.first().name, 'updates'),
|
||||
(self.updated.name, 'updates'),
|
||||
]
|
||||
)
|
||||
|
||||
|
@ -443,7 +443,7 @@ class RebuildReferenceRelationsTests(TestCase):
|
|||
self.assertEqual(
|
||||
result,
|
||||
{
|
||||
'warnings': ['There were 1 references with no matching DocAlias'],
|
||||
'warnings': ['There were 1 references with no matching Document'],
|
||||
'unfound': ['draft-not-found'],
|
||||
}
|
||||
)
|
||||
|
@ -454,6 +454,6 @@ class RebuildReferenceRelationsTests(TestCase):
|
|||
(self.normative.canonical_name(), 'refnorm'),
|
||||
(self.informative.canonical_name(), 'refinfo'),
|
||||
(self.unknown.canonical_name(), 'refunk'),
|
||||
(self.updated.docalias.first().name, 'updates'),
|
||||
(self.updated.name, 'updates'),
|
||||
]
|
||||
)
|
||||
|
|
|
@ -31,7 +31,7 @@ from ietf.community.models import CommunityList
|
|||
from ietf.community.utils import docs_tracked_by_community_list
|
||||
|
||||
from ietf.doc.models import Document, DocHistory, State, DocumentAuthor, DocHistoryAuthor
|
||||
from ietf.doc.models import DocAlias, RelatedDocument, RelatedDocHistory, BallotType, DocReminder
|
||||
from ietf.doc.models import RelatedDocument, RelatedDocHistory, BallotType, DocReminder
|
||||
from ietf.doc.models import DocEvent, ConsensusDocEvent, BallotDocEvent, IRSGBallotDocEvent, NewRevisionDocEvent, StateDocEvent
|
||||
from ietf.doc.models import TelechatDocEvent, DocumentActionHolder, EditedAuthorsDocEvent
|
||||
from ietf.name.models import DocReminderTypeName, DocRelationshipName
|
||||
|
@ -218,7 +218,7 @@ def needed_ballot_positions(doc, active_positions):
|
|||
else:
|
||||
related_set = RelatedDocHistory.objects.none()
|
||||
for rel in related_set.filter(relationship__slug__in=['tops', 'tois', 'tohist', 'toinf', 'tobcp', 'toexp']):
|
||||
if (rel.target.document.std_level_id in ['bcp','ps','ds','std']) or (rel.relationship_id in ['tops','tois','tobcp']):
|
||||
if (rel.target.std_level_id in ['bcp','ps','ds','std']) or (rel.relationship_id in ['tops','tois','tobcp']):
|
||||
needed = two_thirds_rule(recused=len(recuse))
|
||||
break
|
||||
else:
|
||||
|
@ -771,22 +771,22 @@ def rebuild_reference_relations(doc, filenames):
|
|||
errors = []
|
||||
unfound = set()
|
||||
for ( ref, refType ) in refs.items():
|
||||
refdoc = DocAlias.objects.filter(name=ref)
|
||||
refdoc = Document.objects.filter(name=ref)
|
||||
if not refdoc and re.match(r"^draft-.*-\d{2}$", ref):
|
||||
refdoc = DocAlias.objects.filter(name=ref[:-3])
|
||||
refdoc = Document.objects.filter(name=ref[:-3])
|
||||
count = refdoc.count()
|
||||
# As of Dec 2021, DocAlias has a unique constraint on the name field, so count > 1 should not occur
|
||||
if count == 0:
|
||||
unfound.add( "%s" % ref )
|
||||
continue
|
||||
elif count > 1:
|
||||
errors.append("Too many DocAlias objects found for %s"%ref)
|
||||
errors.append("Too many Document objects found for %s"%ref)
|
||||
else:
|
||||
# Don't add references to ourself
|
||||
if doc != refdoc[0].document:
|
||||
if doc != refdoc[0]:
|
||||
RelatedDocument.objects.get_or_create( source=doc, target=refdoc[ 0 ], relationship=DocRelationshipName.objects.get( slug='ref%s' % refType ) )
|
||||
if unfound:
|
||||
warnings.append('There were %d references with no matching DocAlias'%len(unfound))
|
||||
warnings.append('There were %d references with no matching Document'%len(unfound))
|
||||
|
||||
ret = {}
|
||||
if errors:
|
||||
|
@ -821,26 +821,26 @@ def set_replaces_for_document(request, doc, new_replaces, by, email_subject, com
|
|||
|
||||
for d in old_replaces:
|
||||
if d not in new_replaces:
|
||||
other_addrs = gather_address_lists('doc_replacement_changed',doc=d.document)
|
||||
other_addrs = gather_address_lists('doc_replacement_changed',doc=d)
|
||||
to.update(other_addrs.to)
|
||||
cc.update(other_addrs.cc)
|
||||
RelatedDocument.objects.filter(source=doc, target=d, relationship=relationship).delete()
|
||||
if not RelatedDocument.objects.filter(target=d, relationship=relationship):
|
||||
s = 'active' if d.document.expires > timezone.now() else 'expired'
|
||||
d.document.set_state(State.objects.get(type='draft', slug=s))
|
||||
s = 'active' if d.expires > timezone.now() else 'expired'
|
||||
d.set_state(State.objects.get(type='draft', slug=s))
|
||||
|
||||
for d in new_replaces:
|
||||
if d not in old_replaces:
|
||||
other_addrs = gather_address_lists('doc_replacement_changed',doc=d.document)
|
||||
other_addrs = gather_address_lists('doc_replacement_changed',doc=d)
|
||||
to.update(other_addrs.to)
|
||||
cc.update(other_addrs.cc)
|
||||
RelatedDocument.objects.create(source=doc, target=d, relationship=relationship)
|
||||
d.document.set_state(State.objects.get(type='draft', slug='repl'))
|
||||
d.set_state(State.objects.get(type='draft', slug='repl'))
|
||||
|
||||
if d.document.stream_id in ('irtf','ise','iab'):
|
||||
repl_state = State.objects.get(type_id='draft-stream-%s'%d.document.stream_id, slug='repl')
|
||||
d.document.set_state(repl_state)
|
||||
events.append(StateDocEvent.objects.create(doc=d.document, rev=d.document.rev, by=by, type='changed_state', desc="Set stream state to Replaced",state_type=repl_state.type, state=repl_state))
|
||||
if d.stream_id in ('irtf','ise','iab'):
|
||||
repl_state = State.objects.get(type_id='draft-stream-%s'%d.stream_id, slug='repl')
|
||||
d.set_state(repl_state)
|
||||
events.append(StateDocEvent.objects.create(doc=d, rev=d.rev, by=by, type='changed_state', desc="Set stream state to Replaced",state_type=repl_state.type, state=repl_state))
|
||||
|
||||
# make sure there are no lingering suggestions duplicating new replacements
|
||||
RelatedDocument.objects.filter(source=doc, target__in=new_replaces, relationship="possibly-replaces").delete()
|
||||
|
@ -910,7 +910,7 @@ def extract_complete_replaces_ancestor_mapping_for_docs(names):
|
|||
break
|
||||
|
||||
relations = ( RelatedDocument.objects.filter(source__name__in=front, relationship="replaces")
|
||||
.select_related("target").values_list("source__name", "target__docs__name") )
|
||||
.select_related("target").values_list("source__name", "target__name") )
|
||||
if not relations:
|
||||
break
|
||||
|
||||
|
@ -1141,7 +1141,7 @@ def generate_idnits2_rfc_status():
|
|||
def generate_idnits2_rfcs_obsoleted():
|
||||
obsdict = defaultdict(list)
|
||||
for r in RelatedDocument.objects.filter(relationship_id='obs'):
|
||||
obsdict[int(r.target.document.rfc_number)].append(int(r.source.rfc_number))
|
||||
obsdict[int(r.target.rfc_number)].append(int(r.source.rfc_number)) # Aren't these already guaranteed to be ints?
|
||||
for k in obsdict:
|
||||
obsdict[k] = sorted(obsdict[k])
|
||||
return render_to_string('doc/idnits2-rfcs-obsoleted.txt', context={'obsitems':sorted(obsdict.items())})
|
||||
|
|
|
@ -164,12 +164,11 @@ def fill_in_document_table_attributes(docs, have_telechat_date=False):
|
|||
)
|
||||
)
|
||||
for rel in xed_by:
|
||||
d = doc_dict[rel.target.document.id]
|
||||
s = rel_rfc_aliases[rel.source_id]
|
||||
d = doc_dict[rel.target.id]
|
||||
if rel.relationship_id == "obs":
|
||||
d.obsoleted_by_list.append(s)
|
||||
d.obsoleted_by_list.append(rel.source)
|
||||
elif rel.relationship_id == "updates":
|
||||
d.updated_by_list.append(s)
|
||||
d.updated_by_list.append(rel.source)
|
||||
|
||||
def augment_docs_with_related_docs_info(docs):
|
||||
"""Augment all documents with related documents information.
|
||||
|
|
|
@ -958,7 +958,7 @@ def approve_downrefs(request, name):
|
|||
for rel in doc.relateddocument_set.all()
|
||||
if rel.is_downref()
|
||||
and not rel.is_approved_downref()
|
||||
and rel.target.document.type_id == "rfc"
|
||||
and rel.target.type_id == "rfc"
|
||||
]
|
||||
|
||||
downrefs_to_rfc_qs = RelatedDocument.objects.filter(pk__in=[r.pk for r in downrefs_to_rfc])
|
||||
|
@ -974,12 +974,12 @@ def approve_downrefs(request, name):
|
|||
c = DocEvent(type="downref_approved", doc=rel.source,
|
||||
rev=rel.source.rev, by=login)
|
||||
c.desc = "Downref to RFC %s approved by Last Call for %s-%s" % (
|
||||
rel.target.document.rfc_number, rel.source, rel.source.rev)
|
||||
rel.target.rfc_number, rel.source, rel.source.rev)
|
||||
c.save()
|
||||
c = DocEvent(type="downref_approved", doc=rel.target.document,
|
||||
rev=rel.target.document.rev, by=login)
|
||||
c = DocEvent(type="downref_approved", doc=rel.target,
|
||||
rev=rel.target.rev, by=login)
|
||||
c.desc = "Downref to RFC %s approved by Last Call for %s-%s" % (
|
||||
rel.target.document.rfc_number, rel.source, rel.source.rev)
|
||||
rel.target.rfc_number, rel.source, rel.source.rev)
|
||||
c.save()
|
||||
|
||||
return HttpResponseRedirect(doc.get_absolute_url())
|
||||
|
|
|
@ -113,7 +113,7 @@ def send_conflict_review_ad_changed_email(request, review, event):
|
|||
by = request.user.person,
|
||||
event = event,
|
||||
review = review,
|
||||
reviewed_doc = review.relateddocument_set.get(relationship__slug='conflrev').target.document,
|
||||
reviewed_doc = review.relateddocument_set.get(relationship__slug='conflrev').target,
|
||||
review_url = settings.IDTRACKER_BASE_URL+review.get_absolute_url(),
|
||||
)
|
||||
)
|
||||
|
@ -128,7 +128,7 @@ def send_conflict_review_started_email(request, review):
|
|||
cc = addrs.cc,
|
||||
by = request.user.person,
|
||||
review = review,
|
||||
reviewed_doc = review.relateddocument_set.get(relationship__slug='conflrev').target.document,
|
||||
reviewed_doc = review.relateddocument_set.get(relationship__slug='conflrev').target,
|
||||
review_url = settings.IDTRACKER_BASE_URL+review.get_absolute_url(),
|
||||
)
|
||||
)
|
||||
|
@ -137,7 +137,7 @@ def send_conflict_review_started_email(request, review):
|
|||
|
||||
addrs = gather_address_lists('conflrev_requested_iana',doc=review).as_strings(compact=False)
|
||||
email_iana(request,
|
||||
review.relateddocument_set.get(relationship__slug='conflrev').target.document,
|
||||
review.relateddocument_set.get(relationship__slug='conflrev').target,
|
||||
addrs.to,
|
||||
msg,
|
||||
cc=addrs.cc)
|
||||
|
@ -155,7 +155,7 @@ def send_conflict_eval_email(request,review):
|
|||
send_mail_preformatted(request,msg,override=override)
|
||||
addrs = gather_address_lists('ballot_issued_iana',doc=review).as_strings()
|
||||
email_iana(request,
|
||||
review.relateddocument_set.get(relationship__slug='conflrev').target.document,
|
||||
review.relateddocument_set.get(relationship__slug='conflrev').target,
|
||||
addrs.to,
|
||||
msg,
|
||||
addrs.cc)
|
||||
|
@ -247,7 +247,7 @@ def submit(request, name):
|
|||
{'form': form,
|
||||
'next_rev': next_rev,
|
||||
'review' : review,
|
||||
'conflictdoc' : review.relateddocument_set.get(relationship__slug='conflrev').target.document,
|
||||
'conflictdoc' : review.relateddocument_set.get(relationship__slug='conflrev').target,
|
||||
})
|
||||
|
||||
@role_required("Area Director", "Secretariat")
|
||||
|
@ -275,7 +275,7 @@ def edit_ad(request, name):
|
|||
form = AdForm(initial=init)
|
||||
|
||||
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target.document
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target
|
||||
titletext = 'the conflict review of %s-%s' % (conflictdoc.canonical_name(),conflictdoc.rev)
|
||||
return render(request, 'doc/change_ad.html',
|
||||
{'form': form,
|
||||
|
@ -287,7 +287,7 @@ def edit_ad(request, name):
|
|||
def default_approval_text(review):
|
||||
|
||||
current_text = review.text_or_error() # pyflakes:ignore
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target.document
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target
|
||||
if conflictdoc.stream_id=='ise':
|
||||
receiver = 'Independent Submissions Editor'
|
||||
elif conflictdoc.stream_id=='irtf':
|
||||
|
@ -365,7 +365,7 @@ def approve_conflict_review(request, name):
|
|||
return render(request, 'doc/conflict_review/approve.html',
|
||||
dict(
|
||||
review = review,
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target.document,
|
||||
conflictdoc = review.relateddocument_set.get(relationship__slug='conflrev').target,
|
||||
form = form,
|
||||
))
|
||||
|
||||
|
@ -416,7 +416,7 @@ def start_review_sanity_check(request, name):
|
|||
raise Http404
|
||||
|
||||
# sanity check that there's not already a conflict review document for this document
|
||||
if [ rel.source for alias in doc_to_review.docalias.all() for rel in alias.relateddocument_set.filter(relationship='conflrev') ]:
|
||||
if [ rel.source for rel in doc_to_review.targets_related.filter(relationship='conflrev') ]:
|
||||
raise Http404
|
||||
|
||||
return doc_to_review
|
||||
|
@ -452,7 +452,7 @@ def build_conflict_review_document(login, doc_to_review, ad, notify, create_in_s
|
|||
DocAlias.objects.create( name=review_name).docs.add( conflict_review )
|
||||
|
||||
|
||||
conflict_review.relateddocument_set.create(target=DocAlias.objects.get(name=doc_to_review.name),relationship_id='conflrev')
|
||||
conflict_review.relateddocument_set.create(target=doc_to_review, relationship_id='conflrev')
|
||||
|
||||
c = DocEvent(type="added_comment", doc=conflict_review, rev=conflict_review.rev, by=login)
|
||||
c.desc = "IETF conflict review requested"
|
||||
|
|
|
@ -184,9 +184,8 @@ def interesting_doc_relations(doc):
|
|||
|
||||
that_doc_relationships = ('replaces', 'possibly_replaces', 'updates', 'obs', 'became_rfc')
|
||||
|
||||
# TODO: This returns the relationships in database order, which may not be the order we want to display them in.
|
||||
interesting_relations_that = cls.objects.filter(target__docs=target, relationship__in=that_relationships).select_related('source')
|
||||
interesting_relations_that_doc = cls.objects.filter(source=doc, relationship__in=that_doc_relationships).prefetch_related('target__docs')
|
||||
interesting_relations_that = cls.objects.filter(target=target, relationship__in=that_relationships).select_related('source')
|
||||
interesting_relations_that_doc = cls.objects.filter(source=doc, relationship__in=that_doc_relationships).prefetch_related('target')
|
||||
|
||||
return interesting_relations_that, interesting_relations_that_doc
|
||||
|
||||
|
@ -806,7 +805,7 @@ def document_main(request, name, rev=None, document_html=False):
|
|||
if doc.get_state_slug() in ("iesgeval", ) and doc.active_ballot():
|
||||
ballot_summary = needed_ballot_positions(doc, list(doc.active_ballot().active_balloter_positions().values()))
|
||||
|
||||
conflictdoc = doc.related_that_doc('conflrev')[0].document
|
||||
conflictdoc = doc.related_that_doc('conflrev')[0]
|
||||
|
||||
return render(request, "doc/document_conflict_review.html",
|
||||
dict(doc=doc,
|
||||
|
@ -1127,8 +1126,8 @@ def get_diff_revisions(request, name, doc):
|
|||
diff_documents = [doc]
|
||||
diff_documents.extend(
|
||||
Document.objects.filter(
|
||||
docalias__relateddocument__source=doc,
|
||||
docalias__relateddocument__relationship="replaces",
|
||||
relateddocument__source=doc,
|
||||
relateddocument__relationship="replaces",
|
||||
)
|
||||
)
|
||||
|
||||
|
@ -1722,7 +1721,7 @@ def telechat_date(request, name):
|
|||
|
||||
def doc_titletext(doc):
|
||||
if doc.type.slug=='conflrev':
|
||||
conflictdoc = doc.relateddocument_set.get(relationship__slug='conflrev').target.document
|
||||
conflictdoc = doc.relateddocument_set.get(relationship__slug='conflrev').target
|
||||
return 'the conflict review of %s' % conflictdoc.canonical_name()
|
||||
return doc.canonical_name()
|
||||
|
||||
|
|
|
@ -19,7 +19,7 @@ def downref_registry(request):
|
|||
downref_doc_pairs = [ ]
|
||||
downref_relations = RelatedDocument.objects.filter(relationship_id='downref-approval')
|
||||
for rel in downref_relations:
|
||||
downref_doc_pairs.append((rel.target.document, rel.source))
|
||||
downref_doc_pairs.append((rel.target, rel.source))
|
||||
|
||||
return render(request, 'doc/downref.html', {
|
||||
"doc_pairs": downref_doc_pairs,
|
||||
|
@ -38,18 +38,18 @@ def downref_registry_add(request):
|
|||
if form.is_valid():
|
||||
drafts = form.cleaned_data['drafts']
|
||||
rfc = form.cleaned_data['rfc']
|
||||
for da in drafts:
|
||||
RelatedDocument.objects.create(source=da.document,
|
||||
for d in drafts:
|
||||
RelatedDocument.objects.create(source=d,
|
||||
target=rfc, relationship_id='downref-approval')
|
||||
c = DocEvent(type="downref_approved", doc=da.document,
|
||||
rev=da.document.rev, by=login)
|
||||
c = DocEvent(type="downref_approved", doc=d,
|
||||
rev=d.rev, by=login)
|
||||
c.desc = "Downref to RFC %s approved by Last Call for %s-%s" % (
|
||||
rfc.document.rfc_number, da.name, da.document.rev)
|
||||
rfc.rfc_number, d.name, d.rev)
|
||||
c.save()
|
||||
c = DocEvent(type="downref_approved", doc=rfc.document,
|
||||
rev=rfc.document.rev, by=login)
|
||||
c = DocEvent(type="downref_approved", doc=rfc,
|
||||
rev=rfc.rev, by=login)
|
||||
c.desc = "Downref to RFC %s approved by Last Call for %s-%s" % (
|
||||
rfc.document.rfc_number, da.name, da.document.rev)
|
||||
rfc.rfc_number, d.name, d.rev)
|
||||
c.save()
|
||||
|
||||
return HttpResponseRedirect(urlreverse('ietf.doc.views_downref.downref_registry'))
|
||||
|
|
|
@ -23,7 +23,7 @@ from django.utils import timezone
|
|||
|
||||
import debug # pyflakes:ignore
|
||||
|
||||
from ietf.doc.models import ( Document, DocAlias, RelatedDocument, State,
|
||||
from ietf.doc.models import ( Document, RelatedDocument, State,
|
||||
StateType, DocEvent, ConsensusDocEvent, TelechatDocEvent, WriteupDocEvent, StateDocEvent,
|
||||
IanaExpertDocEvent, IESG_SUBSTATE_TAGS)
|
||||
from ietf.doc.mails import ( email_pulled_from_rfc_queue, email_resurrect_requested,
|
||||
|
@ -38,7 +38,7 @@ from ietf.doc.utils import ( add_state_change_event, can_adopt_draft, can_unadop
|
|||
set_replaces_for_document, default_consensus, tags_suffix, can_edit_docextresources,
|
||||
update_doc_extresources )
|
||||
from ietf.doc.lastcall import request_last_call
|
||||
from ietf.doc.fields import SearchableDocAliasesField
|
||||
from ietf.doc.fields import SearchableDocumentsField
|
||||
from ietf.doc.forms import ExtResourceForm
|
||||
from ietf.group.models import Group, Role, GroupFeatures
|
||||
from ietf.iesg.models import TelechatDate
|
||||
|
@ -333,7 +333,7 @@ def change_stream(request, name):
|
|||
))
|
||||
|
||||
class ReplacesForm(forms.Form):
|
||||
replaces = SearchableDocAliasesField(required=False)
|
||||
replaces = SearchableDocumentsField(required=False)
|
||||
comment = forms.CharField(widget=forms.Textarea, required=False, strip=False)
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
|
@ -343,9 +343,9 @@ class ReplacesForm(forms.Form):
|
|||
|
||||
def clean_replaces(self):
|
||||
for d in self.cleaned_data['replaces']:
|
||||
if d.document == self.doc:
|
||||
if d == self.doc:
|
||||
raise forms.ValidationError("An Internet-Draft can't replace itself")
|
||||
if d.document.type_id == "draft" and d.document.get_state_slug() == "rfc":
|
||||
if d.type_id == "draft" and d.get_state_slug() == "rfc":
|
||||
raise forms.ValidationError("An Internet-Draft can't replace an RFC")
|
||||
return self.cleaned_data['replaces']
|
||||
|
||||
|
@ -383,7 +383,7 @@ def replaces(request, name):
|
|||
))
|
||||
|
||||
class SuggestedReplacesForm(forms.Form):
|
||||
replaces = forms.ModelMultipleChoiceField(queryset=DocAlias.objects.all(),
|
||||
replaces = forms.ModelMultipleChoiceField(queryset=Document.objects.all(),
|
||||
label="Suggestions", required=False, widget=forms.CheckboxSelectMultiple,
|
||||
help_text="Select only the documents that are replaced by this document")
|
||||
comment = forms.CharField(label="Optional comment", widget=forms.Textarea, required=False, strip=False)
|
||||
|
@ -673,7 +673,7 @@ def edit_info(request, name):
|
|||
e.save()
|
||||
events.append(e)
|
||||
|
||||
replaces = Document.objects.filter(docalias__relateddocument__source=doc, docalias__relateddocument__relationship="replaces")
|
||||
replaces = Document.objects.filter(targets_related__source=doc, targets_related__relationship="replaces")
|
||||
if replaces:
|
||||
# this should perhaps be somewhere else, e.g. the
|
||||
# place where the replace relationship is established?
|
||||
|
|
|
@ -98,8 +98,8 @@ def change_state(request, name, option=None):
|
|||
relationship__slug__in=STATUSCHANGE_RELATIONS
|
||||
)
|
||||
related_doc_info = [
|
||||
dict(title=rel_doc.target.document.title,
|
||||
canonical_name=rel_doc.target.document.canonical_name(),
|
||||
dict(title=rel_doc.target.title,
|
||||
canonical_name=rel_doc.target.canonical_name(),
|
||||
newstatus=newstatus(rel_doc))
|
||||
for rel_doc in related_docs
|
||||
]
|
||||
|
@ -309,7 +309,7 @@ def default_approval_text(status_change,relateddoc):
|
|||
|
||||
current_text = status_change.text_or_error() # pyflakes:ignore
|
||||
|
||||
if relateddoc.target.document.std_level_id in ('std','ps','ds','bcp',):
|
||||
if relateddoc.target.std_level_id in ('std','ps','ds','bcp',):
|
||||
action = "Protocol Action"
|
||||
else:
|
||||
action = "Document Action"
|
||||
|
@ -320,7 +320,7 @@ def default_approval_text(status_change,relateddoc):
|
|||
dict(status_change=status_change,
|
||||
status_change_url = settings.IDTRACKER_BASE_URL+status_change.get_absolute_url(),
|
||||
relateddoc= relateddoc,
|
||||
relateddoc_url = settings.IDTRACKER_BASE_URL+relateddoc.target.document.get_absolute_url(),
|
||||
relateddoc_url = settings.IDTRACKER_BASE_URL+relateddoc.target.get_absolute_url(),
|
||||
approved_text = current_text,
|
||||
action=action,
|
||||
newstatus=newstatus(relateddoc),
|
||||
|
@ -388,7 +388,7 @@ def approve(request, name):
|
|||
|
||||
for rel in status_change.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS):
|
||||
# Add a document event to each target
|
||||
c = DocEvent(type="added_comment", doc=rel.target.document, rev=rel.target.document.rev, by=login)
|
||||
c = DocEvent(type="added_comment", doc=rel.target, rev=rel.target.rev, by=login)
|
||||
c.desc = "New status of %s approved by the IESG\n%s%s" % (newstatus(rel), settings.IDTRACKER_BASE_URL,reverse('ietf.doc.views_doc.document_main', kwargs={'name': status_change.name}))
|
||||
c.save()
|
||||
|
||||
|
@ -399,7 +399,7 @@ def approve(request, name):
|
|||
init = []
|
||||
for rel in status_change.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS):
|
||||
init.append({"announcement_text" : escape(default_approval_text(status_change,rel)),
|
||||
"label": "Announcement text for %s to %s"%(rel.target.document.canonical_name(),newstatus(rel)),
|
||||
"label": "Announcement text for %s to %s"%(rel.target.canonical_name(),newstatus(rel)),
|
||||
})
|
||||
formset = AnnouncementFormSet(initial=init)
|
||||
for form in formset.forms:
|
||||
|
@ -439,7 +439,7 @@ def clean_helper(form, formtype):
|
|||
|
||||
if not re.match(r'(?i)rfc\d{1,4}',key):
|
||||
errors.append(key+" is not a valid RFC - please use the form RFCn\n")
|
||||
elif not DocAlias.objects.filter(name=key):
|
||||
elif not Document.objects.filter(name=key):
|
||||
errors.append(key+" does not exist\n")
|
||||
|
||||
if new_relations[key] not in STATUSCHANGE_RELATIONS:
|
||||
|
@ -564,10 +564,9 @@ def start_rfc_status_change(request, name=None):
|
|||
DocAlias.objects.create( name= 'status-change-'+form.cleaned_data['document_name']).docs.add(status_change)
|
||||
|
||||
for key in form.cleaned_data['relations']:
|
||||
status_change.relateddocument_set.create(target=DocAlias.objects.get(name=key),
|
||||
status_change.relateddocument_set.create(target=Document.objects.get(name=key),
|
||||
relationship_id=form.cleaned_data['relations'][key])
|
||||
|
||||
|
||||
tc_date = form.cleaned_data['telechat_date']
|
||||
if tc_date:
|
||||
update_telechat(request, status_change, login, tc_date)
|
||||
|
@ -605,11 +604,11 @@ def edit_relations(request, name):
|
|||
|
||||
old_relations={}
|
||||
for rel in status_change.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS):
|
||||
old_relations[rel.target.document.canonical_name()]=rel.relationship.slug
|
||||
old_relations[rel.target.canonical_name()]=rel.relationship.slug
|
||||
new_relations=form.cleaned_data['relations']
|
||||
status_change.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS).delete()
|
||||
for key in new_relations:
|
||||
status_change.relateddocument_set.create(target=DocAlias.objects.get(name=key),
|
||||
status_change.relateddocument_set.create(target=Document.objects.get(name=key),
|
||||
relationship_id=new_relations[key])
|
||||
c = DocEvent(type="added_comment", doc=status_change, rev=status_change.rev, by=login)
|
||||
c.desc = "Affected RFC list changed.\nOLD:"
|
||||
|
@ -626,7 +625,7 @@ def edit_relations(request, name):
|
|||
else:
|
||||
relations={}
|
||||
for rel in status_change.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS):
|
||||
relations[rel.target.document.canonical_name()]=rel.relationship.slug
|
||||
relations[rel.target.canonical_name()]=rel.relationship.slug
|
||||
init = { "relations":relations,
|
||||
}
|
||||
form = EditStatusChangeForm(initial=init)
|
||||
|
@ -653,8 +652,8 @@ def generate_last_call_text(request, doc):
|
|||
settings=settings,
|
||||
requester=requester,
|
||||
expiration_date=expiration_date.strftime("%Y-%m-%d"),
|
||||
changes=['%s from %s to %s\n (%s)'%(rel.target.name.upper(),rel.target.document.std_level.name,newstatus(rel),rel.target.document.title) for rel in doc.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS)],
|
||||
urls=[rel.target.document.get_absolute_url() for rel in doc.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS)],
|
||||
changes=['%s from %s to %s\n (%s)'%(rel.target.name.upper(),rel.target.std_level.name,newstatus(rel),rel.target.title) for rel in doc.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS)],
|
||||
urls=[rel.target.get_absolute_url() for rel in doc.relateddocument_set.filter(relationship__slug__in=STATUSCHANGE_RELATIONS)],
|
||||
cc=cc
|
||||
)
|
||||
)
|
||||
|
|
|
@ -69,7 +69,7 @@ class GroupStatsTests(TestCase):
|
|||
a = WgDraftFactory()
|
||||
b = WgDraftFactory()
|
||||
RelatedDocument.objects.create(
|
||||
source=a, target=b.docalias.first(), relationship_id="refnorm"
|
||||
source=a, target=b, relationship_id="refnorm"
|
||||
)
|
||||
|
||||
def test_group_stats(self):
|
||||
|
@ -95,7 +95,7 @@ class GroupDocDependencyTests(TestCase):
|
|||
a = WgDraftFactory()
|
||||
b = WgDraftFactory()
|
||||
RelatedDocument.objects.create(
|
||||
source=a, target=b.docalias.first(), relationship_id="refnorm"
|
||||
source=a, target=b, relationship_id="refnorm"
|
||||
)
|
||||
|
||||
def test_group_document_dependencies(self):
|
||||
|
|
|
@ -756,7 +756,7 @@ def dependencies(request, acronym, group_type=None):
|
|||
relationship__slug__startswith="ref",
|
||||
)
|
||||
|
||||
both_rfcs = Q(source__states__slug="rfc", target__docs__states__slug="rfc")
|
||||
both_rfcs = Q(source__states__slug="rfc", target__states__slug="rfc")
|
||||
inactive = Q(source__states__slug__in=["expired", "repl"])
|
||||
attractor = Q(target__name__in=["rfc5000", "rfc5741"])
|
||||
removed = Q(source__states__slug__in=["auth-rm", "ietf-rm"])
|
||||
|
@ -770,19 +770,19 @@ def dependencies(request, acronym, group_type=None):
|
|||
|
||||
links = set()
|
||||
for x in relations:
|
||||
target_state = x.target.document.get_state_slug("draft")
|
||||
target_state = x.target.get_state_slug("draft")
|
||||
if target_state != "rfc" or x.is_downref():
|
||||
links.add(x)
|
||||
|
||||
replacements = RelatedDocument.objects.filter(
|
||||
relationship__slug="replaces",
|
||||
target__docs__in=[x.target.document for x in links],
|
||||
target__in=[x.target for x in links],
|
||||
)
|
||||
|
||||
for x in replacements:
|
||||
links.add(x)
|
||||
|
||||
nodes = set([x.source for x in links]).union([x.target.document for x in links])
|
||||
nodes = set([x.source for x in links]).union([x.target for x in links])
|
||||
graph = {
|
||||
"nodes": [
|
||||
{
|
||||
|
@ -805,7 +805,7 @@ def dependencies(request, acronym, group_type=None):
|
|||
"links": [
|
||||
{
|
||||
"source": x.source.canonical_name(),
|
||||
"target": x.target.document.canonical_name(),
|
||||
"target": x.target.canonical_name(),
|
||||
"rel": "downref" if x.is_downref() else x.relationship.slug,
|
||||
}
|
||||
for x in links
|
||||
|
|
|
@ -34,7 +34,7 @@ def all_id_txt():
|
|||
rfc_aliases = dict(DocAlias.objects.filter(name__startswith="rfc",
|
||||
docs__states=State.objects.get(type="draft", slug="rfc")).values_list("docs__name", "name"))
|
||||
|
||||
replacements = dict(RelatedDocument.objects.filter(target__docs__states=State.objects.get(type="draft", slug="repl"),
|
||||
replacements = dict(RelatedDocument.objects.filter(target__states=State.objects.get(type="draft", slug="repl"),
|
||||
relationship="replaces").values_list("target__name", "source__name"))
|
||||
|
||||
|
||||
|
@ -115,7 +115,7 @@ def all_id2_txt():
|
|||
rfc_aliases = dict(DocAlias.objects.filter(name__startswith="rfc",
|
||||
docs__states=State.objects.get(type="draft", slug="rfc")).values_list("docs__name", "name"))
|
||||
|
||||
replacements = dict(RelatedDocument.objects.filter(target__docs__states=State.objects.get(type="draft", slug="repl"),
|
||||
replacements = dict(RelatedDocument.objects.filter(target__states=State.objects.get(type="draft", slug="repl"),
|
||||
relationship="replaces").values_list("target__name", "source__name"))
|
||||
|
||||
revision_time = dict(DocEvent.objects.filter(type="new_revision", doc__name__startswith="draft-").order_by('time').values_list("doc__name", "time"))
|
||||
|
|
|
@ -52,8 +52,13 @@ class IndexTests(TestCase):
|
|||
|
||||
RelatedDocument.objects.create(
|
||||
relationship=DocRelationshipName.objects.get(slug="replaces"),
|
||||
source=Document.objects.create(type_id="draft", rev="00", name="draft-test-replacement"),
|
||||
target=draft.docalias.get(name__startswith="draft"))
|
||||
source=Document.objects.create(
|
||||
type_id="draft",
|
||||
rev="00",
|
||||
name="draft-test-replacement"
|
||||
),
|
||||
target=draft
|
||||
)
|
||||
|
||||
txt = all_id_txt()
|
||||
self.assertTrue(draft.name + "-" + draft.rev in txt)
|
||||
|
@ -111,8 +116,12 @@ class IndexTests(TestCase):
|
|||
draft.set_state(State.objects.get(type="draft", slug="repl"))
|
||||
RelatedDocument.objects.create(
|
||||
relationship=DocRelationshipName.objects.get(slug="replaces"),
|
||||
source=Document.objects.create(type_id="draft", rev="00", name="draft-test-replacement"),
|
||||
target=draft.docalias.get(name__startswith="draft"))
|
||||
source=Document.objects.create(
|
||||
type_id="draft",
|
||||
rev="00",
|
||||
name="draft-test-replacement"
|
||||
),
|
||||
target=draft)
|
||||
|
||||
t = get_fields(all_id2_txt())
|
||||
self.assertEqual(t[5], "draft-test-replacement")
|
||||
|
|
|
@ -66,7 +66,7 @@ def get_doc_section(doc):
|
|||
elif doc.type_id == 'statchg':
|
||||
protocol_action = False
|
||||
for relation in doc.relateddocument_set.filter(relationship__slug__in=('tops','tois','tohist','toinf','tobcp','toexp')):
|
||||
if relation.relationship_id in ('tops','tois') or relation.target.document.std_level_id in ('std','ds','ps'):
|
||||
if relation.relationship_id in ('tops','tois') or relation.target.std_level_id in ('std','ds','ps'):
|
||||
protocol_action = True
|
||||
if protocol_action:
|
||||
s = "2.3"
|
||||
|
@ -186,7 +186,7 @@ def fill_in_agenda_docs(date, sections, docs=None):
|
|||
|
||||
doc.review_assignments = review_assignments_for_docs.get(doc.name, [])
|
||||
elif doc.type_id == "conflrev":
|
||||
doc.conflictdoc = doc.relateddocument_set.get(relationship__slug='conflrev').target.document
|
||||
doc.conflictdoc = doc.relateddocument_set.get(relationship__slug='conflrev').target
|
||||
elif doc.type_id == "charter":
|
||||
pass
|
||||
|
||||
|
@ -219,4 +219,4 @@ def agenda_data(date=None):
|
|||
fill_in_agenda_docs(date, sections)
|
||||
fill_in_agenda_management_issues(date, sections)
|
||||
|
||||
return { 'date': date.isoformat(), 'sections': sections }
|
||||
return { 'date': date.isoformat(), 'sections': sections }
|
||||
|
|
|
@ -17,7 +17,7 @@ from django.utils.html import escape
|
|||
import debug # pyflakes:ignore
|
||||
|
||||
from ietf.doc.models import DocEvent, BallotPositionDocEvent, TelechatDocEvent
|
||||
from ietf.doc.models import Document, DocAlias, State, RelatedDocument
|
||||
from ietf.doc.models import Document, State, RelatedDocument
|
||||
from ietf.doc.factories import WgDraftFactory, IndividualDraftFactory, ConflictReviewFactory, BaseDocumentFactory, CharterFactory, WgRfcFactory, IndividualRfcFactory
|
||||
from ietf.doc.utils import create_ballot_if_not_open
|
||||
from ietf.group.factories import RoleFactory, GroupFactory
|
||||
|
@ -108,7 +108,7 @@ class IESGAgendaTests(TestCase):
|
|||
mars = GroupFactory(acronym='mars',parent=Group.objects.get(acronym='farfut'))
|
||||
wgdraft = WgDraftFactory(name='draft-ietf-mars-test', group=mars, intended_std_level_id='ps')
|
||||
rfc = IndividualRfcFactory.create(stream_id='irtf', rfc_number=6666, std_level_id='inf', )
|
||||
wgdraft.relateddocument_set.create(target=rfc.docalias.get(name='rfc6666'), relationship_id='refnorm')
|
||||
wgdraft.relateddocument_set.create(target=rfc, relationship_id='refnorm')
|
||||
ise_draft = IndividualDraftFactory(name='draft-imaginary-independent-submission')
|
||||
ise_draft.stream = StreamName.objects.get(slug="ise")
|
||||
ise_draft.save_with_history([DocEvent(doc=ise_draft, rev=ise_draft.rev, type="changed_stream", by=Person.objects.get(user__username="secretary"), desc="Test")])
|
||||
|
@ -238,7 +238,7 @@ class IESGAgendaTests(TestCase):
|
|||
|
||||
relation = RelatedDocument.objects.create(
|
||||
source=statchg,
|
||||
target=DocAlias.objects.filter(name__startswith='rfc', docs__std_level="ps")[0],
|
||||
target=Document.objects.filter(type_id="rfc", std_level="ps").first(),
|
||||
relationship_id="tohist")
|
||||
|
||||
statchg.group = Group.objects.get(acronym="mars")
|
||||
|
@ -256,7 +256,7 @@ class IESGAgendaTests(TestCase):
|
|||
self.assertTrue(statchg in agenda_data(date_str)["sections"]["2.3.3"]["docs"])
|
||||
|
||||
# 3.3 document status changes
|
||||
relation.target = DocAlias.objects.filter(name__startswith='rfc', docs__std_level="inf")[0]
|
||||
relation.target = Document.objects.filter(type_id="rfc", std_level="inf").first()
|
||||
relation.save()
|
||||
|
||||
statchg.group = Group.objects.get(acronym="mars")
|
||||
|
|
|
@ -32,10 +32,10 @@ def telechat_page_count(date=None, docs=None):
|
|||
pages_for_action += d.pages or 0
|
||||
elif d.type_id == 'statchg':
|
||||
for rel in d.related_that_doc(STATUSCHANGE_RELATIONS):
|
||||
pages_for_action += rel.document.pages or 0
|
||||
pages_for_action += rel.pages or 0
|
||||
elif d.type_id == 'conflrev':
|
||||
for rel in d.related_that_doc('conflrev'):
|
||||
pages_for_action += rel.document.pages or 0
|
||||
pages_for_action += rel.pages or 0
|
||||
else:
|
||||
pass
|
||||
|
||||
|
@ -43,10 +43,10 @@ def telechat_page_count(date=None, docs=None):
|
|||
for d in for_approval-set(drafts):
|
||||
if d.type_id == 'statchg':
|
||||
for rel in d.related_that_doc(STATUSCHANGE_RELATIONS):
|
||||
related_pages += rel.document.pages or 0
|
||||
related_pages += rel.pages or 0
|
||||
elif d.type_id == 'conflrev':
|
||||
for rel in d.related_that_doc('conflrev'):
|
||||
related_pages += rel.document.pages or 0
|
||||
related_pages += rel.pages or 0
|
||||
else:
|
||||
# There's really nothing to rely on to give a reading load estimate for charters
|
||||
pass
|
||||
|
|
|
@ -172,7 +172,7 @@ def agenda_json(request, date=None):
|
|||
|
||||
elif doc.type_id == 'conflrev':
|
||||
docinfo['rev'] = doc.rev
|
||||
td = doc.relateddocument_set.get(relationship__slug='conflrev').target.document
|
||||
td = doc.relateddocument_set.get(relationship__slug='conflrev').target
|
||||
docinfo['target-docname'] = td.canonical_name()
|
||||
docinfo['target-title'] = td.title
|
||||
docinfo['target-rev'] = td.rev
|
||||
|
|
|
@ -94,7 +94,7 @@ admin.site.register(IprDocRel, IprDocRelAdmin)
|
|||
|
||||
class RelatedIprAdmin(admin.ModelAdmin):
|
||||
list_display = ['source', 'target', 'relationship', ]
|
||||
search_fields = ['source__name', 'target__name', 'target__docs__name', ]
|
||||
search_fields = ['source__name', 'target__name', ]
|
||||
raw_id_fields = ['source', 'target', ]
|
||||
admin.site.register(RelatedIpr, RelatedIprAdmin)
|
||||
|
||||
|
|
|
@ -41,24 +41,17 @@ def iprs_from_docs(aliases,**kwargs):
|
|||
iprdocrels += document.ipr(**kwargs)
|
||||
return list(set([i.disclosure for i in iprdocrels]))
|
||||
|
||||
def related_docs(alias, relationship=('replaces', 'obs')):
|
||||
def related_docs(doc, relationship=('replaces', 'obs')):
|
||||
"""Returns list of related documents"""
|
||||
|
||||
results = []
|
||||
for doc in alias.docs.all():
|
||||
results += list(doc.docalias.all())
|
||||
|
||||
rels = []
|
||||
for doc in alias.docs.all():
|
||||
rels += list(doc.all_relations_that_doc(relationship))
|
||||
results = [doc]
|
||||
|
||||
rels = list(doc.document.all_relations_that_doc(relationship))
|
||||
|
||||
for rel in rels:
|
||||
rel_aliases = list(rel.target.document.docalias.all())
|
||||
|
||||
for x in rel_aliases:
|
||||
x.related = rel
|
||||
x.relation = rel.relationship.revname
|
||||
results += rel_aliases
|
||||
rel.target.related = rel
|
||||
rel.target.relation = rel.relationship.revname
|
||||
results += [x.target for x in rels]
|
||||
|
||||
return list(set(results))
|
||||
|
||||
|
|
|
@ -96,35 +96,35 @@ class Recipient(models.Model):
|
|||
addrs = []
|
||||
if 'doc' in kwargs:
|
||||
for reldoc in kwargs['doc'].related_that_doc(('conflrev','tohist','tois','tops')):
|
||||
addrs.extend(Recipient.objects.get(slug='doc_authors').gather(**{'doc':reldoc.document}))
|
||||
addrs.extend(Recipient.objects.get(slug='doc_authors').gather(**{'doc':reldoc}))
|
||||
return addrs
|
||||
|
||||
def gather_doc_affecteddoc_group_chairs(self, **kwargs):
|
||||
addrs = []
|
||||
if 'doc' in kwargs:
|
||||
for reldoc in kwargs['doc'].related_that_doc(('conflrev','tohist','tois','tops')):
|
||||
addrs.extend(Recipient.objects.get(slug='doc_group_chairs').gather(**{'doc':reldoc.document}))
|
||||
addrs.extend(Recipient.objects.get(slug='doc_group_chairs').gather(**{'doc':reldoc}))
|
||||
return addrs
|
||||
|
||||
def gather_doc_affecteddoc_notify(self, **kwargs):
|
||||
addrs = []
|
||||
if 'doc' in kwargs:
|
||||
for reldoc in kwargs['doc'].related_that_doc(('conflrev','tohist','tois','tops')):
|
||||
addrs.extend(Recipient.objects.get(slug='doc_notify').gather(**{'doc':reldoc.document}))
|
||||
addrs.extend(Recipient.objects.get(slug='doc_notify').gather(**{'doc':reldoc}))
|
||||
return addrs
|
||||
|
||||
def gather_conflict_review_stream_manager(self, **kwargs):
|
||||
addrs = []
|
||||
if 'doc' in kwargs:
|
||||
for reldoc in kwargs['doc'].related_that_doc(('conflrev',)):
|
||||
addrs.extend(Recipient.objects.get(slug='doc_stream_manager').gather(**{'doc':reldoc.document}))
|
||||
addrs.extend(Recipient.objects.get(slug='doc_stream_manager').gather(**{'doc':reldoc}))
|
||||
return addrs
|
||||
|
||||
def gather_conflict_review_steering_group(self,**kwargs):
|
||||
addrs = []
|
||||
if 'doc' in kwargs:
|
||||
for reldoc in kwargs['doc'].related_that_doc(('conflrev',)):
|
||||
if reldoc.document.stream_id=='irtf':
|
||||
if reldoc.stream_id=='irtf':
|
||||
addrs.append('"Internet Research Steering Group" <irsg@irtf.org>')
|
||||
return addrs
|
||||
|
||||
|
|
|
@ -68,8 +68,7 @@ class SecrTelechatTestCase(TestCase):
|
|||
ad = Person.objects.get(user__username="ad")
|
||||
draft = WgDraftFactory(ad=ad, intended_std_level_id='ps', states=[('draft-iesg','pub-req'),])
|
||||
rfc = IndividualRfcFactory.create(stream_id='irtf', rfc_number=6666, std_level_id='inf')
|
||||
draft.relateddocument_set.create(target=rfc.docalias.get(name='rfc6666'),
|
||||
relationship_id='refnorm')
|
||||
draft.relateddocument_set.create(target=rfc, relationship_id='refnorm')
|
||||
create_ballot_if_not_open(None, draft, ad, 'approve')
|
||||
d = get_next_telechat_date()
|
||||
date = d.strftime('%Y-%m-%d')
|
||||
|
|
|
@ -313,7 +313,7 @@ def doc_detail(request, date, name):
|
|||
|
||||
# if this is a conflict review document add referenced document
|
||||
if doc.type_id == 'conflrev':
|
||||
conflictdoc = doc.relateddocument_set.get(relationship__slug='conflrev').target.document
|
||||
conflictdoc = doc.relateddocument_set.get(relationship__slug='conflrev').target
|
||||
else:
|
||||
conflictdoc = None
|
||||
|
||||
|
|
|
@ -85,13 +85,13 @@
|
|||
{% if downrefs %}
|
||||
<h2 id="downrefs">Downward References</h2>
|
||||
{% for ref in downrefs %}
|
||||
<p>Add {{ref.target.document.canonical_name}}
|
||||
({{ref.target.document.std_level}} - {{ref.target.document.stream.desc}})
|
||||
<p>Add {{ref.target.canonical_name}}
|
||||
({{ref.target.std_level}} - {{ref.target.stream.desc}})
|
||||
to downref registry.<br>
|
||||
{% if not ref.target.document.std_level %}
|
||||
{% if not ref.target.std_level %}
|
||||
+++ Warning: The standards level has not been set yet!!!<br>
|
||||
{% endif %}
|
||||
{% if not ref.target.document.stream %}
|
||||
{% if not ref.target.stream %}
|
||||
+++ Warning: document stream has not been set yet!!!<br>
|
||||
{% endif %}
|
||||
{% endfor %}</p>
|
||||
|
|
|
@ -82,7 +82,7 @@ class StatisticsTests(TestCase):
|
|||
DocAlias.objects.create(name=referencing_draft.name).docs.add(referencing_draft)
|
||||
RelatedDocument.objects.create(
|
||||
source=referencing_draft,
|
||||
target=draft.docalias.first(),
|
||||
target=draft,
|
||||
relationship=DocRelationshipName.objects.get(slug="refinfo")
|
||||
)
|
||||
NewRevisionDocEvent.objects.create(
|
||||
|
|
|
@ -563,11 +563,11 @@ def document_stats(request, stats_type=None):
|
|||
bins = defaultdict(set)
|
||||
|
||||
cite_relationships = list(DocRelationshipName.objects.filter(slug__in=['refnorm', 'refinfo', 'refunk', 'refold']))
|
||||
person_filters &= Q(documentauthor__document__docalias__relateddocument__relationship__in=cite_relationships)
|
||||
person_filters &= Q(documentauthor__document__relateddocument__relationship__in=cite_relationships)
|
||||
|
||||
person_qs = Person.objects.filter(person_filters)
|
||||
|
||||
for name, citations in person_qs.values_list("name").annotate(Count("documentauthor__document__docalias__relateddocument")):
|
||||
for name, citations in person_qs.values_list("name").annotate(Count("documentauthor__document__relateddocument")):
|
||||
bins[citations or 0].add(name)
|
||||
|
||||
total_persons = count_bins(bins)
|
||||
|
@ -587,11 +587,11 @@ def document_stats(request, stats_type=None):
|
|||
bins = defaultdict(set)
|
||||
|
||||
cite_relationships = list(DocRelationshipName.objects.filter(slug__in=['refnorm', 'refinfo', 'refunk', 'refold']))
|
||||
person_filters &= Q(documentauthor__document__docalias__relateddocument__relationship__in=cite_relationships)
|
||||
person_filters &= Q(documentauthor__document__relateddocument__relationship__in=cite_relationships)
|
||||
|
||||
person_qs = Person.objects.filter(person_filters)
|
||||
|
||||
values = person_qs.values_list("name", "documentauthor__document").annotate(Count("documentauthor__document__docalias__relateddocument"))
|
||||
values = person_qs.values_list("name", "documentauthor__document").annotate(Count("documentauthor__document__relateddocument"))
|
||||
for name, ts in itertools.groupby(values.order_by("name"), key=lambda t: t[0]):
|
||||
h_index = compute_hirsch_index([citations for _, document, citations in ts])
|
||||
bins[h_index or 0].add(name)
|
||||
|
|
|
@ -28,8 +28,7 @@ import debug # pyflakes:ignore
|
|||
from ietf.doc.models import Document
|
||||
from ietf.group.models import Group
|
||||
from ietf.ietfauth.utils import has_role
|
||||
from ietf.doc.fields import SearchableDocAliasesField
|
||||
from ietf.doc.models import DocAlias
|
||||
from ietf.doc.fields import SearchableDocumentsField
|
||||
from ietf.ipr.mail import utc_from_string
|
||||
from ietf.meeting.models import Meeting
|
||||
from ietf.message.models import Message
|
||||
|
@ -684,9 +683,9 @@ class SubmissionAutoUploadForm(SubmissionBaseUploadForm):
|
|||
if self.cleaned_data['replaces']:
|
||||
names_replaced = [s.strip() for s in self.cleaned_data['replaces'].split(',')]
|
||||
self.cleaned_data['replaces'] = ','.join(names_replaced)
|
||||
aliases_replaced = DocAlias.objects.filter(name__in=names_replaced)
|
||||
if len(names_replaced) != len(aliases_replaced):
|
||||
known_names = aliases_replaced.values_list('name', flat=True)
|
||||
documents_replaced = Document.objects.filter(name__in=names_replaced)
|
||||
if len(names_replaced) != len(documents_replaced):
|
||||
known_names = documents_replaced.values_list('name', flat=True)
|
||||
unknown_names = [n for n in names_replaced if n not in known_names]
|
||||
self.add_error(
|
||||
'replaces',
|
||||
|
@ -694,27 +693,27 @@ class SubmissionAutoUploadForm(SubmissionBaseUploadForm):
|
|||
'Unknown Internet-Draft name(s): ' + ', '.join(unknown_names)
|
||||
),
|
||||
)
|
||||
for alias in aliases_replaced:
|
||||
if alias.document.name == self.filename:
|
||||
for doc in documents_replaced:
|
||||
if doc.name == self.filename:
|
||||
self.add_error(
|
||||
'replaces',
|
||||
forms.ValidationError("An Internet-Draft cannot replace itself"),
|
||||
)
|
||||
elif alias.document.type_id != "draft":
|
||||
elif doc.type_id != "draft":
|
||||
self.add_error(
|
||||
'replaces',
|
||||
forms.ValidationError("An Internet-Draft can only replace another Internet-Draft"),
|
||||
)
|
||||
elif alias.document.get_state_slug() == "rfc":
|
||||
elif doc.get_state_slug() == "rfc":
|
||||
self.add_error(
|
||||
'replaces',
|
||||
forms.ValidationError("An Internet-Draft cannot replace another Internet-Draft that has become an RFC"),
|
||||
)
|
||||
elif alias.document.get_state_slug('draft-iesg') in ('approved', 'ann', 'rfcqueue'):
|
||||
elif doc.get_state_slug('draft-iesg') in ('approved', 'ann', 'rfcqueue'):
|
||||
self.add_error(
|
||||
'replaces',
|
||||
forms.ValidationError(
|
||||
alias.name + " is approved by the IESG and cannot be replaced"
|
||||
doc.name + " is approved by the IESG and cannot be replaced"
|
||||
),
|
||||
)
|
||||
return cleaned_data
|
||||
|
@ -755,22 +754,20 @@ class SubmitterForm(NameEmailForm):
|
|||
return line
|
||||
|
||||
class ReplacesForm(forms.Form):
|
||||
replaces = SearchableDocAliasesField(required=False, help_text="Any Internet-Drafts that this document replaces (approval required for replacing an Internet-Draft you are not the author of)")
|
||||
replaces = SearchableDocumentsField(required=False, help_text="Any Internet-Drafts that this document replaces (approval required for replacing an Internet-Draft you are not the author of)")
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
self.name = kwargs.pop("name")
|
||||
super(ReplacesForm, self).__init__(*args, **kwargs)
|
||||
|
||||
def clean_replaces(self):
|
||||
for alias in self.cleaned_data['replaces']:
|
||||
if alias.document.name == self.name:
|
||||
for doc in self.cleaned_data['replaces']:
|
||||
if doc.name == self.name:
|
||||
raise forms.ValidationError("An Internet-Draft cannot replace itself.")
|
||||
if alias.document.type_id != "draft":
|
||||
if doc.type_id != "draft":
|
||||
raise forms.ValidationError("An Internet-Draft can only replace another Internet-Draft")
|
||||
if alias.document.get_state_slug() == "rfc":
|
||||
raise forms.ValidationError("An Internet-Draft cannot replace an RFC")
|
||||
if alias.document.get_state_slug('draft-iesg') in ('approved','ann','rfcqueue'):
|
||||
raise forms.ValidationError(alias.name+" is approved by the IESG and cannot be replaced")
|
||||
if doc.get_state_slug('draft-iesg') in ('approved','ann','rfcqueue'):
|
||||
raise forms.ValidationError(doc.name+" is approved by the IESG and cannot be replaced")
|
||||
return self.cleaned_data['replaces']
|
||||
|
||||
class EditSubmissionForm(forms.ModelForm):
|
||||
|
|
|
@ -302,7 +302,7 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
submission = Submission.objects.get(name=name)
|
||||
self.assertEqual(submission.submitter, email.utils.formataddr((submitter_name, submitter_email)))
|
||||
self.assertEqual([] if submission.replaces == "" else submission.replaces.split(','),
|
||||
[ d.name for d in DocAlias.objects.filter(pk__in=replaces) ])
|
||||
[ d.name for d in Document.objects.filter(pk__in=replaces) ])
|
||||
self.assertCountEqual(
|
||||
[str(r) for r in submission.external_resources.all()],
|
||||
[str(r) for r in extresources] if extresources else [],
|
||||
|
@ -369,9 +369,8 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
|
||||
# supply submitter info, then draft should be in and ready for approval
|
||||
mailbox_before = len(outbox)
|
||||
replaced_alias = draft.docalias.first()
|
||||
r = self.supply_extra_metadata(name, status_url, author.ascii, author.email().address.lower(),
|
||||
replaces=[str(replaced_alias.pk), str(sug_replaced_alias.pk)])
|
||||
replaces=[str(draft.pk), str(sug_replaced_draft.pk)])
|
||||
|
||||
self.assertEqual(r.status_code, 302)
|
||||
status_url = r["Location"]
|
||||
|
@ -419,7 +418,7 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
self.assertEqual(authors[0].person, author)
|
||||
self.assertEqual(set(draft.formal_languages.all()), set(FormalLanguageName.objects.filter(slug="json")))
|
||||
self.assertEqual(draft.relations_that_doc("replaces").count(), 1)
|
||||
self.assertTrue(draft.relations_that_doc("replaces").first().target, replaced_alias)
|
||||
self.assertTrue(draft.relations_that_doc("replaces").first().target, draft)
|
||||
self.assertEqual(draft.relations_that_doc("possibly-replaces").count(), 1)
|
||||
self.assertTrue(draft.relations_that_doc("possibly-replaces").first().target, sug_replaced_alias)
|
||||
self.assertEqual(len(outbox), mailbox_before + 5)
|
||||
|
@ -1142,7 +1141,7 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
self.verify_bibxml_ids_creation(draft)
|
||||
|
||||
def test_submit_update_individual(self):
|
||||
IndividualDraftFactory(name='draft-ietf-random-thing', states=[('draft','rfc')], other_aliases=['rfc9999',], pages=5)
|
||||
IndividualDraftFactory(name='draft-ietf-random-thing', states=[('draft','active'),('draft-iesg','approved')], pages=5)
|
||||
ad=Person.objects.get(user__username='ad')
|
||||
# Group of None here does not reflect real individual submissions
|
||||
draft = IndividualDraftFactory(group=None, ad = ad, authors=[ad,], notify='aliens@example.mars', pages=5)
|
||||
|
@ -1152,23 +1151,14 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
status_url, author = self.do_submission(name,rev)
|
||||
mailbox_before = len(outbox)
|
||||
|
||||
replaced_alias = draft.docalias.first()
|
||||
r = self.supply_extra_metadata(name, status_url, "Submitter Name", "author@example.com", replaces=[str(replaced_alias.pk)])
|
||||
r = self.supply_extra_metadata(name, status_url, "Submitter Name", "author@example.com", replaces=[str(draft.pk)])
|
||||
self.assertEqual(r.status_code, 200)
|
||||
self.assertContains(r, 'cannot replace itself')
|
||||
self._assert_extresources_in_table(r, [])
|
||||
self._assert_extresources_form(r, [])
|
||||
|
||||
replaced_alias = DocAlias.objects.get(name='draft-ietf-random-thing')
|
||||
r = self.supply_extra_metadata(name, status_url, "Submitter Name", "author@example.com", replaces=[str(replaced_alias.pk)])
|
||||
self.assertEqual(r.status_code, 200)
|
||||
self.assertContains(r, 'cannot replace an RFC')
|
||||
self._assert_extresources_in_table(r, [])
|
||||
self._assert_extresources_form(r, [])
|
||||
|
||||
replaced_alias.document.set_state(State.objects.get(type='draft-iesg',slug='approved'))
|
||||
replaced_alias.document.set_state(State.objects.get(type='draft',slug='active'))
|
||||
r = self.supply_extra_metadata(name, status_url, "Submitter Name", "author@example.com", replaces=[str(replaced_alias.pk)])
|
||||
replaced = Document.objects.get(name='draft-ietf-random-thing')
|
||||
r = self.supply_extra_metadata(name, status_url, "Submitter Name", "author@example.com", replaces=[str(replaced.pk)])
|
||||
self.assertEqual(r.status_code, 200)
|
||||
self.assertContains(r, 'approved by the IESG and cannot')
|
||||
self._assert_extresources_in_table(r, [])
|
||||
|
@ -1262,7 +1252,7 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
status_url,
|
||||
"Submitter Name",
|
||||
"submitter@example.com",
|
||||
replaces=[str(replaced_draft.docalias.first().pk)],
|
||||
replaces=[str(replaced_draft.pk)],
|
||||
)
|
||||
|
||||
submission = Submission.objects.get(name=name, rev=rev)
|
||||
|
@ -1412,7 +1402,7 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
"edit-pages": "123",
|
||||
"submitter-name": "Some Random Test Person",
|
||||
"submitter-email": "random@example.com",
|
||||
"replaces": [str(draft.docalias.first().pk)],
|
||||
"replaces": [str(draft.pk)],
|
||||
"edit-note": "no comments",
|
||||
"authors-0-name": "Person 1",
|
||||
"authors-0-email": "person1@example.com",
|
||||
|
@ -1431,7 +1421,7 @@ class SubmitTests(BaseSubmitTestCase):
|
|||
self.assertEqual(submission.pages, 123)
|
||||
self.assertEqual(submission.note, "no comments")
|
||||
self.assertEqual(submission.submitter, "Some Random Test Person <random@example.com>")
|
||||
self.assertEqual(submission.replaces, draft.docalias.first().name)
|
||||
self.assertEqual(submission.replaces, draft.name)
|
||||
self.assertEqual(submission.state_id, "manual")
|
||||
|
||||
authors = submission.authors
|
||||
|
@ -3100,7 +3090,7 @@ class SubmissionUploadFormTests(BaseSubmitTestCase):
|
|||
# can't replace RFC
|
||||
rfc = WgRfcFactory()
|
||||
draft = WgDraftFactory(states=[("draft", "rfc")])
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc.docalias.first())
|
||||
draft.relateddocument_set.create(relationship_id="became_rfc", target=rfc)
|
||||
form = SubmissionAutoUploadForm(
|
||||
request_factory.get('/some/url'),
|
||||
data={'user': auth.user.username, 'replaces': draft.name},
|
||||
|
|
|
@ -504,7 +504,7 @@ def update_replaces_from_submission(request, submission, draft):
|
|||
if request.user.is_authenticated:
|
||||
is_chair_of = list(Group.objects.filter(role__person__user=request.user, role__name="chair"))
|
||||
|
||||
replaces = DocAlias.objects.filter(name__in=submission.replaces.split(",")).prefetch_related("docs", "docs__group")
|
||||
replaces = Document.objects.filter(name__in=submission.replaces.split(",")).prefetch_related("group")
|
||||
existing_replaces = list(draft.related_that_doc("replaces"))
|
||||
existing_suggested = set(draft.related_that_doc("possibly-replaces"))
|
||||
|
||||
|
@ -516,14 +516,12 @@ def update_replaces_from_submission(request, submission, draft):
|
|||
if r in existing_replaces:
|
||||
continue
|
||||
|
||||
rdoc = r.document
|
||||
|
||||
if rdoc == draft:
|
||||
if r == draft:
|
||||
continue
|
||||
|
||||
if (is_secretariat
|
||||
or (draft.group in is_chair_of and (rdoc.group.type_id == "individ" or rdoc.group in is_chair_of))
|
||||
or (submitter_email and rdoc.documentauthor_set.filter(email__address__iexact=submitter_email).exists())):
|
||||
or (draft.group in is_chair_of and (r.group.type_id == "individ" or r.group in is_chair_of))
|
||||
or (submitter_email and r.documentauthor_set.filter(email__address__iexact=submitter_email).exists())):
|
||||
approved.append(r)
|
||||
else:
|
||||
if r not in existing_suggested:
|
||||
|
|
|
@ -488,12 +488,15 @@ def update_docs_from_rfc_index(index_data, errata_data, skip_older_than_date=Non
|
|||
def parse_relation_list(l):
|
||||
res = []
|
||||
for x in l:
|
||||
if x[:3] in ("NIC", "IEN", "STD", "RTR"):
|
||||
# try translating this to RFCs that we can handle
|
||||
# sensibly; otherwise we'll have to ignore them
|
||||
l = DocAlias.objects.filter(name__startswith="rfc", docs__docalias__name=x.lower())
|
||||
else:
|
||||
l = DocAlias.objects.filter(name=x.lower())
|
||||
# This lookup wasn't finding anything but maybe some STD and we know
|
||||
# if the STD had more than one RFC the wrong thing happens
|
||||
#
|
||||
#if x[:3] in ("NIC", "IEN", "STD", "RTR"):
|
||||
# # try translating this to RFCs that we can handle
|
||||
# # sensibly; otherwise we'll have to ignore them
|
||||
# l = DocAlias.objects.filter(name__startswith="rfc", docs__docalias__name=x.lower())
|
||||
#else:
|
||||
l = Document.objects.filter(name=x.lower())
|
||||
|
||||
for a in l:
|
||||
if a not in res:
|
||||
|
|
|
@ -14,7 +14,7 @@ from django.utils import timezone
|
|||
|
||||
import debug # pyflakes:ignore
|
||||
|
||||
from ietf.doc.factories import WgDraftFactory
|
||||
from ietf.doc.factories import WgDraftFactory, RfcFactory
|
||||
from ietf.doc.models import Document, DocAlias, DocEvent, DeletedEvent, DocTagName, RelatedDocument, State, StateDocEvent
|
||||
from ietf.doc.utils import add_state_change_event
|
||||
from ietf.group.factories import GroupFactory
|
||||
|
@ -235,9 +235,7 @@ class RFCSyncTests(TestCase):
|
|||
# too, but for testing purposes ...
|
||||
doc.action_holders.add(doc.ad) # not normally set, but add to be sure it's cleared
|
||||
|
||||
updated_doc = Document.objects.create(name="draft-ietf-something")
|
||||
DocAlias.objects.create(name=updated_doc.name).docs.add(updated_doc)
|
||||
DocAlias.objects.create(name="rfc123").docs.add(updated_doc)
|
||||
RfcFactory(rfc_number=123)
|
||||
|
||||
today = date_today()
|
||||
|
||||
|
@ -360,7 +358,7 @@ class RFCSyncTests(TestCase):
|
|||
self.assertTrue(DocAlias.objects.filter(name="bcp1", docs=doc))
|
||||
self.assertTrue(DocAlias.objects.filter(name="fyi1", docs=doc))
|
||||
self.assertTrue(DocAlias.objects.filter(name="std1", docs=doc))
|
||||
self.assertTrue(RelatedDocument.objects.filter(source=doc, target__name="rfc123", relationship="updates"))
|
||||
self.assertTrue(RelatedDocument.objects.filter(source=doc, target__name="rfc123", relationship="updates").exists())
|
||||
self.assertEqual(doc.title, "A Testing RFC")
|
||||
self.assertEqual(doc.abstract, "This is some interesting text.")
|
||||
self.assertEqual(doc.get_state_slug(), "rfc")
|
||||
|
@ -602,4 +600,4 @@ class RFCEditorUndoTests(TestCase):
|
|||
e = DeletedEvent.objects.all().order_by("-time", "-id")[0]
|
||||
|
||||
e.content_type.model_class().objects.create(**json.loads(e.json))
|
||||
self.assertTrue(StateDocEvent.objects.filter(desc="First", doc=draft))
|
||||
self.assertTrue(StateDocEvent.objects.filter(desc="First", doc=draft))
|
||||
|
|
|
@ -35,7 +35,7 @@
|
|||
<a href="{% url 'ietf.doc.views_doc.document_main' name=name %}">{{ name|prettystdname }}</a>
|
||||
</td>
|
||||
<td>
|
||||
<b>{{ ref.target.document.title }}</b>
|
||||
<b>{{ ref.target.title }}</b>
|
||||
<br>
|
||||
<a class="btn btn-primary btn-sm"
|
||||
href="{% url 'ietf.doc.views_doc.document_references' name %}"
|
||||
|
@ -51,12 +51,12 @@
|
|||
</a>
|
||||
</td>
|
||||
<td>
|
||||
{% if ref.target.document.type_id == "rfc" %}
|
||||
{% with ref.target.document.std_level as lvl %}
|
||||
{% if ref.target.type_id == "rfc" %}
|
||||
{% with ref.target.std_level as lvl %}
|
||||
{% if lvl %}{{ lvl }}{% endif %}
|
||||
{% endwith %}
|
||||
{% else %}
|
||||
{% with ref.target.document.intended_std_level as lvl %}
|
||||
{% with ref.target.intended_std_level as lvl %}
|
||||
{% if lvl %}{{ lvl }}{% endif %}
|
||||
{% endwith %}
|
||||
{% endif %}
|
||||
|
|
|
@ -52,7 +52,7 @@
|
|||
<td class="edit"></td>
|
||||
<td>
|
||||
{% for rel in relation_group.list %}
|
||||
{{ rel.target.document.canonical_name|upper|urlize_ietf_docs }}{% if not forloop.last %},{% endif %}
|
||||
{{ rel.target.canonical_name|upper|urlize_ietf_docs }}{% if not forloop.last %},{% endif %}
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
|
|
|
@ -33,7 +33,7 @@ No IPR declarations have been submitted directly on this I-D.
|
|||
{% if downrefs %}
|
||||
The document contains these normative downward references.
|
||||
See RFC 3967 for additional information:
|
||||
{% for ref in downrefs %} {{ref.target.document.canonical_name}}: {{ref.target.document.title}} ({{ref.target.document.std_level}} - {{ref.target.document.stream.desc}})
|
||||
{% for ref in downrefs %} {{ref.target.canonical_name}}: {{ref.target.title}} ({{ref.target.std_level}} - {{ref.target.stream.desc}})
|
||||
{% endfor %}{%endif%}
|
||||
|
||||
{% endautoescape %}
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
{% load ietf_filters %}{% load mail_filters %}{% autoescape off %}From: The IESG <iesg-secretary@ietf.org>
|
||||
To: {{ to }}{% if cc %}
|
||||
Cc: {{ cc }}{% endif %}
|
||||
Subject: {{action}}: {{relateddoc.target.document.title}} to {{newstatus}}
|
||||
Subject: {{action}}: {{relateddoc.target.title}} to {{newstatus}}
|
||||
|
||||
{% filter wordwrap:78 %}The IESG has approved changing the status of the following document:
|
||||
- {{relateddoc.target.document.title }}
|
||||
({{relateddoc.target.document.canonical_name }}) to {{ newstatus }}
|
||||
- {{relateddoc.target.title }}
|
||||
({{relateddoc.target.canonical_name }}) to {{ newstatus }}
|
||||
|
||||
This {{action|lower}} is documented at:
|
||||
{{status_change_url}}
|
||||
|
|
|
@ -165,13 +165,13 @@ Parts Copyright (c) 2009 The IETF Trust, all rights reserved.
|
|||
{% if downrefs %}
|
||||
<p>If APPROVED - The Secretariat will add to the downref registry:<br>
|
||||
{% for ref in downrefs %}
|
||||
+ Add {{ref.target.document.canonical_name}}
|
||||
({{ref.target.document.std_level}} - {{ref.target.document.stream.desc}})
|
||||
+ Add {{ref.target.canonical_name}}
|
||||
({{ref.target.std_level}} - {{ref.target.stream.desc}})
|
||||
to downref registry.<br>
|
||||
{% if not ref.target.document.std_level %}
|
||||
{% if not ref.target.std_level %}
|
||||
+++ Warning: The standards level has not been set yet!!!<br>
|
||||
{% endif %}
|
||||
{% if not ref.target.document.stream %}
|
||||
{% if not ref.target.stream %}
|
||||
+++ Warning: document stream has not been set yet!!!<br>
|
||||
{% endif %}
|
||||
{% endfor %}</p>
|
||||
|
|
|
@ -12,11 +12,12 @@ from django.utils.encoding import smart_str
|
|||
import debug # pyflakes:ignore
|
||||
|
||||
from ietf.doc.models import Document, DocAlias, State, DocumentAuthor, DocEvent, RelatedDocument, NewRevisionDocEvent
|
||||
from ietf.doc.factories import IndividualDraftFactory, ConflictReviewFactory, StatusChangeFactory, WgDraftFactory, WgRfcFactory
|
||||
from ietf.group.models import Group, GroupHistory, Role, RoleHistory
|
||||
from ietf.iesg.models import TelechatDate
|
||||
from ietf.ipr.models import HolderIprDisclosure, IprDocRel, IprDisclosureStateName, IprLicenseTypeName
|
||||
from ietf.meeting.models import Meeting, ResourceAssociation
|
||||
from ietf.name.models import StreamName, DocRelationshipName, RoomResourceName, ConstraintName
|
||||
from ietf.name.models import DocRelationshipName, RoomResourceName, ConstraintName
|
||||
from ietf.person.models import Person, Email
|
||||
from ietf.group.utils import setup_default_community_list_for_group
|
||||
from ietf.review.models import (ReviewRequest, ReviewerSettings, ReviewResultName, ReviewTypeName, ReviewTeamSettings )
|
||||
|
@ -316,7 +317,7 @@ def make_test_data():
|
|||
doc_alias = DocAlias.objects.create(name=draft.name)
|
||||
doc_alias.docs.add(draft)
|
||||
|
||||
RelatedDocument.objects.create(source=draft, target=old_alias, relationship=DocRelationshipName.objects.get(slug='replaces'))
|
||||
RelatedDocument.objects.create(source=draft, target=old_draft, relationship=DocRelationshipName.objects.get(slug='replaces'))
|
||||
old_draft.set_state(State.objects.get(type='draft', slug='repl'))
|
||||
|
||||
DocumentAuthor.objects.create(
|
||||
|
@ -391,37 +392,27 @@ def make_test_data():
|
|||
)
|
||||
|
||||
# an independent submission before review
|
||||
doc = Document.objects.create(name='draft-imaginary-independent-submission',type_id='draft',rev='00',
|
||||
title="Some Independent Notes on Imagination")
|
||||
doc.set_state(State.objects.get(used=True, type="draft", slug="active"))
|
||||
DocAlias.objects.create(name=doc.name).docs.add(doc)
|
||||
IndividualDraftFactory(title="Some Independent Notes on Imagination")
|
||||
|
||||
# an irtf submission mid review
|
||||
doc = Document.objects.create(name='draft-imaginary-irtf-submission', type_id='draft',rev='00',
|
||||
stream=StreamName.objects.get(slug='irtf'), title="The Importance of Research Imagination")
|
||||
docalias = DocAlias.objects.create(name=doc.name)
|
||||
docalias.docs.add(doc)
|
||||
doc.set_state(State.objects.get(type="draft", slug="active"))
|
||||
crdoc = Document.objects.create(name='conflict-review-imaginary-irtf-submission', type_id='conflrev',
|
||||
rev='00', notify="fsm@ietf.org", title="Conflict Review of IRTF Imagination Document")
|
||||
DocAlias.objects.create(name=crdoc.name).docs.add(crdoc)
|
||||
crdoc.set_state(State.objects.get(name='Needs Shepherd', type__slug='conflrev'))
|
||||
crdoc.relateddocument_set.create(target=docalias,relationship_id='conflrev')
|
||||
doc = IndividualDraftFactory(name="draft-imaginary-irtf-submission", stream_id="irtf", title="The Importance of Research Imagination")
|
||||
ConflictReviewFactory(name="conflict-review-imaginary-irtf-submission", review_of=doc, notify="fsm@ietf.org", title="Conflict Review of IRTF Imagination Document")
|
||||
|
||||
# A status change mid review
|
||||
iesg = Group.objects.get(acronym='iesg')
|
||||
doc = Document.objects.create(name='status-change-imaginary-mid-review',type_id='statchg', rev='00',
|
||||
notify="fsm@ietf.org", group=iesg, title="Status Change Review without Imagination")
|
||||
doc.set_state(State.objects.get(slug='needshep',type__slug='statchg'))
|
||||
docalias = DocAlias.objects.create(name='status-change-imaginary-mid-review')
|
||||
docalias.docs.add(doc)
|
||||
doc = StatusChangeFactory(
|
||||
name='status-change-imaginary-mid-review',
|
||||
notify="fsm@ietf.org",
|
||||
group=iesg,
|
||||
title="Status Change Review without Imagination",
|
||||
states= [State.objects.get(type_id="statchg",slug="needshep")]
|
||||
)
|
||||
|
||||
# Some things for a status change to affect
|
||||
def rfc_for_status_change_test_factory(name,rfc_num,std_level_id):
|
||||
target_rfc = Document.objects.create(name=name, type_id='draft', std_level_id=std_level_id, notify="%s@ietf.org"%name)
|
||||
target_rfc.set_state(State.objects.get(slug='rfc',type__slug='draft'))
|
||||
DocAlias.objects.create(name=name).docs.add(target_rfc)
|
||||
DocAlias.objects.create(name='rfc%d'%rfc_num).docs.add(target_rfc)
|
||||
target_rfc = WgRfcFactory(rfc_number=rfc_num, std_level_id=std_level_id)
|
||||
source_draft = WgDraftFactory(name=name, states=[("draft","rfc")], notify=f"{name}@ietf.org")
|
||||
source_draft.relateddocument_set.create(relationship_id="became_rfc", target=target_rfc)
|
||||
return target_rfc
|
||||
rfc_for_status_change_test_factory('draft-ietf-random-thing',9999,'ps')
|
||||
rfc_for_status_change_test_factory('draft-ietf-random-otherthing',9998,'inf')
|
||||
|
|
Loading…
Reference in a new issue