arxiv.submission.domain.event package¶
Data structures for submissions events.
Events have unique identifiers generated from their data (creation, agent, submission).
Events provide methods to update a submission based on the event data.
Events provide validation methods for event data.
Writing new events/commands¶
Events/commands are implemented as classes that inherit from Event.
It should:
Be a dataclass (i.e. be decorated with
dataclasses.dataclass()).Define (using
dataclasses.field()) associated data.Implement a validation method with the signature
validate(self, submission: Submission) -> None(see below).Implement a projection method with the signature
project(self, submission: Submission) -> Submission:that mutates the passeddomain.submission.Submissioninstance. The projection must not generate side-effects, because it will be called any time we are generating the state of a submission. If you need to generate a side-effect, see Registering event callbacks.Be fully documented. Be sure that the class docstring fully describes the meaning of the event/command, and that both public and private methods have at least a summary docstring.
Have a corresponding
unittest.TestCaseinarxiv.submission.domain.tests.test_events.
Adding validation to events¶
Each command/event class should implement an instance method
validate(self, submission: Submission) -> None that raises
InvalidEvent exceptions if the data on the event instance is not
valid.
For clarity, it’s a good practice to individuate validation steps as separate
private instance methods, and call them from the public validate method.
This makes it easier to identify which validation criteria are being applied,
in what order, and what those criteria mean.
See SetPrimaryClassification for an example.
We could consider standalone validation functions for validation checks that are performed on several event types (instead of just private instance methods).
Registering event callbacks¶
The base Event provides support for callbacks that are executed when
an event instance is committed. To attach a callback to an event type, use the
Event.bind() decorator. For example:
@SetTitle.bind()
def do_this_when_a_title_is_set(event, before, after, agent):
...
return []
Callbacks must have the signature (event: Event, before: Submission,
after: Submission, creator: Agent) -> Iterable[Event]. event is the
event instance being committed that triggered the callback. before and
after are the states of the submission before and after the event was
applied, respectively. agent is the agent responsible for any subsequent
events created by the callback, and should be used for that purpose.
The callback should not concern itself with persistence; that is handled by
Event.commit(). Any mutations of submission should be made by returning
the appropriate command/event instances.
The circumstances under which the callback is executed can be controlled by
passing a condition callable to the decorator. This should have the signature
(event: Event, before: Submission, after: Submission, creator: Agent) ->
bool; if it returns True, the callback will be executed. For example:
@SetTitle.bind(condition=lambda e, b, a, c: e.title == 'foo')
def do_this_when_a_title_is_set_to_foo(event, before, after, agent):
...
return []
When do things actually happen?¶
Callbacks are triggered when the commit() method is called,
usually by core.save(). Normally, any event instances returned
by the callback are applied and committed right away, in order.
Setting config.ENABLE_CALLBACKS=0 will disable callbacks
entirely.
-
class
arxiv.submission.domain.event.AddClassifierResults(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, classifier=<Classifiers.CLASSIC: 'classic'>, results=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventAdd the results of a classifier to a submission.
-
NAME= 'add classifer results'¶
-
NAMED= 'classifier results added'¶
-
classifier= 'classic'¶
-
-
class
arxiv.submission.domain.event.AddFeature(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, feature_type=<Type.WORD_COUNT: 'words'>, feature_value=0)[source]¶ Bases:
arxiv.submission.domain.event.base.EventAdd feature metadata to a submission.
-
NAME= 'add feature metadata'¶
-
NAMED= 'feature metadata added'¶
-
feature_type= 'words'¶
-
feature_value= 0¶
-
-
class
arxiv.submission.domain.event.AddSecondaryClassification(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, category=None)[source]¶ Bases:
arxiv.submission.domain.event.base.EventAdd a secondary
Classificationto a submission.-
NAME= 'add cross-list classification'¶
-
NAMED= 'cross-list classification added'¶
-
category= None¶
-
project(submission)[source]¶ Add a
Classificationas a secondary classification.- Return type
-
-
class
arxiv.submission.domain.event.Announce(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, arxiv_id=None)[source]¶ Bases:
arxiv.submission.domain.event.base.EventAnnounce the current version of the submission.
-
NAME= 'publish submission'¶
-
NAMED= 'submission announced'¶
-
arxiv_id= None¶
-
-
class
arxiv.submission.domain.event.ConfirmAuthorship(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, submitter_is_author=True)[source]¶ Bases:
arxiv.submission.domain.event.base.EventThe submitting user asserts whether they are an author of the paper.
-
NAME= 'confirm that submitter is an author'¶
-
NAMED= 'submitter authorship status confirmed'¶
-
-
class
arxiv.submission.domain.event.ConfirmCompiledPreview(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventConfirm that the submitter successfully compiled a preview.
-
NAME= 'confirm submission preview is compiled'¶
-
NAMED= 'confirmed that submission preview was compiled'¶
-
-
class
arxiv.submission.domain.event.ConfirmContactInformation(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventSubmitter has verified their contact information.
-
NAME= 'confirm contact information'¶
-
NAMED= 'contact information confirmed'¶
-
project(submission)[source]¶ Update
Submission.submitter_contact_verified.- Return type
-
-
class
arxiv.submission.domain.event.ConfirmPolicy(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventThe submitting user accepts the arXiv submission policy.
-
NAME= 'confirm policy acceptance'¶
-
NAMED= 'policy acceptance confirmed'¶
-
-
class
arxiv.submission.domain.event.ConfirmPreview(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventConfirm that the paper and abstract previews are acceptable.
-
NAME= 'approve submission preview'¶
-
NAMED= 'submission preview approved'¶
-
validate(submission)[source]¶ Validate data for
ConfirmPreview.- Return type
None
-
-
class
arxiv.submission.domain.event.CreateSubmission(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventCreation of a new
domain.submission.Submission.-
NAME= 'create submission'¶
-
NAMED= 'submission created'¶
-
project(submission=None)[source]¶ Create a new
domain.submission.Submission.- Return type
-
-
class
arxiv.submission.domain.event.CreateSubmissionVersion(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventCreates a new version of a submission.
Takes the submission back to “working” state; the user or client may make additional changes before finalizing the submission.
-
NAME= 'create a new version'¶
-
NAMED= 'new version created'¶
-
-
class
arxiv.submission.domain.event.FinalizeSubmission(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventSend the submission to the queue for announcement.
-
NAME= 'finalize submission for announcement'¶
-
NAMED= 'submission finalized'¶
-
REQUIRED= ['creator', 'primary_classification', 'submitter_contact_verified', 'submitter_accepts_policy', 'license', 'source_content', 'metadata']¶
-
REQUIRED_METADATA= ['title', 'abstract', 'authors_display']¶
-
-
class
arxiv.submission.domain.event.Reclassify(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, category=None)[source]¶ Bases:
arxiv.submission.domain.event.base.EventReclassify a submission.
-
NAME= 'reclassify submission'¶
-
NAMED= 'submission reclassified'¶
-
category= None¶
-
-
class
arxiv.submission.domain.event.RemoveSecondaryClassification(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, category=None)[source]¶ Bases:
arxiv.submission.domain.event.base.EventRemove secondary
Classificationfrom submission.-
NAME= 'remove cross-list classification'¶
-
NAMED= 'cross-list classification removed'¶
-
category= None¶
-
-
class
arxiv.submission.domain.event.Rollback(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventRoll back to the most recent announced version, or delete.
-
NAME= 'roll back or delete'¶
-
NAMED= 'rolled back or deleted'¶
-
-
class
arxiv.submission.domain.event.SetACMClassification(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, acm_class='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the ACM classification codes of a submission.
-
MAX_LENGTH= 160¶
-
NAME= 'update ACM classification'¶
-
NAMED= 'ACM classification updated'¶
-
acm_class= ''¶ E.g. F.2.2; I.2.7
-
project(submission)[source]¶ Update the ACM classification on a
domain.submission.Submission.- Return type
-
-
class
arxiv.submission.domain.event.SetAbstract(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, abstract='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the abstract of a submission.
-
MAX_LENGTH= 1920¶
-
MIN_LENGTH= 20¶
-
NAME= 'update abstract'¶
-
NAMED= 'abstract updated'¶
-
abstract= ''¶
-
project(submission)[source]¶ Update the abstract on a
domain.submission.Submission.- Return type
-
-
class
arxiv.submission.domain.event.SetAuthors(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, authors=<factory>, authors_display=None)[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the authors on a
domain.submission.Submission.-
NAME= 'update authors'¶
-
NAMED= 'authors updated'¶
The authors string may be provided.
-
-
class
arxiv.submission.domain.event.SetComments(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, comments='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the comments of a submission.
-
MAX_LENGTH= 400¶
-
NAME= 'update comments'¶
-
NAMED= 'comments updated'¶
-
comments= ''¶
-
project(submission)[source]¶ Update the comments on a
domain.submission.Submission.- Return type
-
-
class
arxiv.submission.domain.event.SetDOI(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, doi='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the external DOI of a submission.
-
NAME= 'add a DOI'¶
-
NAMED= 'DOI added'¶
-
doi= ''¶
-
project(submission)[source]¶ Update the doi on a
domain.submission.Submission.- Return type
-
-
class
arxiv.submission.domain.event.SetJournalReference(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, journal_ref='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the journal reference of a submission.
-
NAME= 'add a journal reference'¶
-
NAMED= 'journal reference added'¶
-
journal_ref= ''¶
-
project(submission)[source]¶ Update the journal reference on a
domain.submission.Submission.- Return type
-
-
class
arxiv.submission.domain.event.SetLicense(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, license_name=None, license_uri=None)[source]¶ Bases:
arxiv.submission.domain.event.base.EventThe submitter has selected a license for their submission.
-
NAME= 'select distribution license'¶
-
NAMED= 'distribution license selected'¶
-
license_name= None¶
-
license_uri= None¶
-
-
class
arxiv.submission.domain.event.SetMSCClassification(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, msc_class='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the MSC classification codes of a submission.
-
MAX_LENGTH= 160¶
-
NAME= 'update MSC classification'¶
-
NAMED= 'MSC classification updated'¶
-
static
cleanup(value)[source]¶ Perform some light fixes on the MSC classification value.
- Return type
-
msc_class= ''¶
-
project(submission)[source]¶ Update the MSC classification on a
domain.submission.Submission.- Return type
-
-
class
arxiv.submission.domain.event.SetPrimaryClassification(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, category=None)[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the primary classification of a submission.
-
NAME= 'set primary classification'¶
-
NAMED= 'primary classification set'¶
-
category= None¶
-
-
class
arxiv.submission.domain.event.SetReportNumber(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, report_num='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the report number of a submission.
-
NAME= 'update report number'¶
-
NAMED= 'report number updated'¶
-
project(submission)[source]¶ Set report number on a
domain.submission.Submission.- Return type
-
report_num= ''¶
-
-
class
arxiv.submission.domain.event.SetTitle(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, title='')[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the title of a submission.
-
ALLOWED_HTML= ['br', 'sup', 'sub', 'hr', 'em', 'strong', 'h']¶
-
MAX_LENGTH= 240¶
-
MIN_LENGTH= 5¶
-
NAME= 'update title'¶
-
NAMED= 'title updated'¶
-
project(submission)[source]¶ Update the title on a
domain.submission.Submission.- Return type
-
title= ''¶
-
-
class
arxiv.submission.domain.event.SetUploadPackage(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, identifier=<factory>, checksum=<factory>, uncompressed_size=0, compressed_size=0, source_format=<Format.UNKNOWN: None>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventSet the upload workspace for this submission.
-
NAME= 'set the upload package'¶
-
NAMED= 'upload package set'¶
-
compressed_size= 0¶
-
project(submission)[source]¶ Replace
SubmissionContentmetadata on the submission.- Return type
-
source_format= None¶
-
uncompressed_size= 0¶
-
validate(submission)[source]¶ Validate data for
SetUploadPackage.- Return type
None
-
-
class
arxiv.submission.domain.event.UnConfirmCompiledPreview(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventUnconfirm that the submitter successfully compiled a preview.
-
NAME= 'unconfirm submission preview is compiled'¶
-
NAMED= 'unconfirmed that submission preview was compiled'¶
-
-
class
arxiv.submission.domain.event.UnFinalizeSubmission(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventWithdraw the submission from the queue for announcement.
-
NAME= 're-open submission for modification'¶
-
NAMED= 'submission re-opened for modification'¶
-
-
class
arxiv.submission.domain.event.UnsetUploadPackage(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventUnset the upload workspace for this submission.
-
NAME= 'unset the upload package'¶
-
NAMED= 'upload package unset'¶
-
validate(submission)[source]¶ Validate data for
UnsetUploadPackage.- Return type
None
-
-
class
arxiv.submission.domain.event.UpdateUploadPackage(creator, created=None, proxy=None, client=None, submission_id=None, committed=False, before=None, after=None, event_type=<factory>, event_version=<factory>, checksum=<factory>, uncompressed_size=0, compressed_size=0, source_format=<Format.UNKNOWN: None>)[source]¶ Bases:
arxiv.submission.domain.event.base.EventUpdate the upload workspace on this submission.
-
NAME= 'update the upload package'¶
-
NAMED= 'upload package updated'¶
-
compressed_size= 0¶
-
project(submission)[source]¶ Replace
SubmissionContentmetadata on the submission.- Return type
-
source_format= None¶
-
uncompressed_size= 0¶
-
validate(submission)[source]¶ Validate data for
SetUploadPackage.- Return type
None
-
Subpackages¶
Submodules¶
- arxiv.submission.domain.event.base module
- arxiv.submission.domain.event.flag module
- arxiv.submission.domain.event.process module
- arxiv.submission.domain.event.proposal module
- arxiv.submission.domain.event.request module
- arxiv.submission.domain.event.util module
- arxiv.submission.domain.event.validators module