Example #1
0
def reduction_script(request, reduction_id, instrument_name):
    """
        Display a script representation of a reduction process.
        
        @param request: request object
        @param reduction_id: pk of the ReductionProcess object
    """
    
    logger.debug("Reduction: %s instrument_name=%s"%(inspect.stack()[0][3],instrument_name))
    
    instrument_name_lowercase = str.lower(str(instrument_name))
    
    instrument_forms = view_util.import_module_from_app(instrument_name_lowercase,'forms')
    
    data = instrument_forms.ReductionOptions.data_from_db(request.user, reduction_id)
    
    breadcrumbs = Breadcrumbs()
    breadcrumbs.append_reduction(instrument_name_lowercase)
    breadcrumbs.append("reduction %s"%reduction_id,".")
    breadcrumbs.append("script")
    
    template_values = {'reduction_name': data['reduction_name'],
                       'breadcrumbs': breadcrumbs,
                       'code': instrument_forms.ReductionOptions.as_mantid_script(data) }
    template_values = reduction_server.view_util.fill_template_values(request, **template_values)
    logger.debug(pprint.pformat(template_values))
    return render_to_response('reduction/reduction_script.html', template_values,
                              context_instance=RequestContext(request))
Example #2
0
def reduction_jobs(request, instrument_name):
    """
        Return a list of the remote reduction jobs.
        The jobs are those that are owned by the user and have an
        entry in the database.
        
        @param request: request object
    """
    logger.debug("Reduction: %s instrument_name=%s"%(inspect.stack()[0][3],instrument_name))
    
    instrument_name = str(instrument_name).lower()
    
    jobs = RemoteJob.objects.filter(transaction__owner=request.user).filter(reduction__instrument__name=instrument_name )
    status_data = []
    for job in jobs:
        if not job.transaction.is_active or job.reduction.get_config() is not None:
            continue
        j_data = {'remote_id': job.remote_id,
                  'id': job.pk,
                  'name': job.reduction.name,
                  'reduction_id': job.reduction.id,
                  'start_date': job.transaction.start_time,
                  'data': job.reduction.data_file,
                  'trans_id': job.transaction.trans_id,
                  'experiments': job.reduction.get_experiments()
                 }
        status_data.append(j_data)
    
    # Get config jobs
    config_jobs = RemoteJobSet.objects.filter(transaction__owner=request.user).filter(configuration__instrument__name=instrument_name )
    config_data = []
    for job in config_jobs:
        if not job.transaction.is_active:
            continue
        j_data = {'id': job.id,
                  'config_id': job.configuration.id,
                  'name': job.configuration.name,
                  'trans_id': job.transaction.trans_id,
                  'experiments': job.configuration.get_experiments()
                 }
        config_data.append(j_data)
        
    breadcrumbs = Breadcrumbs()
    breadcrumbs.append_reduction(str.lower(str(instrument_name)))
    breadcrumbs.append("jobs")
    template_values = {'status_data': status_data,
                       'config_data': config_data,
                       'back_url': request.path,
                       'breadcrumbs': breadcrumbs,
                       'instrument' : instrument_name, }
    template_values = reduction_server.view_util.fill_template_values(request, **template_values)
    logger.debug(pprint.pformat(template_values))   
    return render_to_response('%s/reduction_jobs.html' % instrument_name,
                              template_values,
                              context_instance=RequestContext(request))
Example #3
0
def reduction_submit(request, reduction_id, instrument_name):
    """
        Submit a reduction script to Fermi.

        @param request: request object
        @param reduction_id: pk of the ReductionProcess object
    """
    
    logger.debug("Reduction: %s instrument_name=%s"%(inspect.stack()[0][3],instrument_name))
    
    instrument_name_lowercase = str.lower(str(instrument_name))
    instrument_forms = view_util.import_module_from_app(instrument_name_lowercase,'forms')
    
    # TODO: Make sure the submission errors are clearly reported
    reduction_proc = get_object_or_404(ReductionProcess, pk=reduction_id, owner=request.user)

    # Start a new transaction
    transaction = remote.view_util.transaction(request, start=True)
    if transaction is None:
        
        breadcrumbs = Breadcrumbs()
        breadcrumbs.append_reduction(instrument_name_lowercase)
        breadcrumbs.append_reduction_options(instrument_name_lowercase, reduction_id)
        
        messages.add_message(request, messages.ERROR, "Could not connect to Fermi and establish transaction.")
        template_values = {'back_url': reverse('reduction_options',
                                               kwargs={'reduction_id' : reduction_id, 'instrument_name': instrument_name_lowercase}),
                           'breadcrumbs': breadcrumbs, }
        template_values = reduction_server.view_util.fill_template_values(request, **template_values)
        logger.debug(pprint.pformat(template_values))
        return render_to_response('remote/failed_connection.html', template_values,
                                  context_instance=RequestContext(request))

    data = instrument_forms.ReductionOptions.data_from_db(request.user, reduction_id)
    code = instrument_forms.ReductionOptions.as_mantid_script(data, transaction.directory)
    jobID = remote.view_util.submit_job(request, transaction, code)
    if jobID is not None:
        job = RemoteJob(reduction=reduction_proc,
                        remote_id=jobID,
                        properties=reduction_proc.properties,
                        transaction=transaction)
        job.save()
        logger.debug("Created a RemoteJob: %s",job)
    
    messages.add_message(request, messages.SUCCESS, 
                         message="Job %s sucessfully submitted. <a href='%s' class='message-link'>Click to see the results this job </a>."%
                                     (job.id, reverse('reduction_query', kwargs={'remote_job_id' : job.id, 'instrument_name' : instrument_name_lowercase})))
    
    return redirect(reverse('reduction_options',
                                  kwargs={'reduction_id' : reduction_id, 
                                          'instrument_name': instrument_name_lowercase}))
Example #4
0
def experiment(request, ipts, instrument_name):
    """
        List of reductions and configurations for a given experiment
        @param request: request object
        @param ipts: experiment name
        
        #TODO create new reduction using a pre-existing one as a template
    """
    
    logger.debug("Reduction: %s instrument_name=%s"%(inspect.stack()[0][3],instrument_name))
    
    instrument_name_capitals = str.capitalize(str(instrument_name))
    instrument_name_lowercase = str.lower(str(instrument_name))
    
    # Get experiment object
    uncategorized = Experiment.objects.get_uncategorized(instrument_name)
    try:
        experiment_obj = Experiment.objects.get(name=ipts)
    except:
        experiment_obj = uncategorized
    
    IS_UNCATEGORIZED = experiment_obj.is_uncategorized()
    
    #RIC: Don't understand this one!
    reduction_start_form = forms.ReductionStart(request.GET)

    icat_ipts = {}
    if not IS_UNCATEGORIZED:
        icat_ipts = get_ipts_info(str.capitalize(str(instrument_name)), ipts)

    # Get all the user's reductions
    red_list = []
    if 'run_number' in request.GET:
        red_list = ReductionProcess.objects.filter(owner=request.user,
                                                   data_file__contains=request.GET['run_number'])
        if len(red_list) == 0:
            create_url = reverse('reduction_options',
                                  kwargs={'instrument_name': instrument_name_lowercase})
            create_url += '?reduction_name=Reduction for r%s' % request.GET['run_number']
            create_url += '&expt_id=%d' % experiment_obj.id
            create_url += '&data_file=%s' % request.GET['run_number']
            return redirect(create_url)
    else:
        for item in ReductionProcess.objects.filter(owner=request.user,
                                                    experiments=experiment_obj).order_by('data_file'):
            if not item in red_list:
                red_list.append(item)

    reductions = []
    for r in red_list:
        data_dict = r.get_data_dict()
        data_dict['id'] = r.id
        data_dict['config'] = r.get_config()
        # For this reduction_process (r) check if there more more jobs, if so get the most recent!
        latest_job = view_util.get_latest_job(request, r)
        if latest_job is not None:
            data_dict['completed_job'] = reverse('reduction_query',
                                                 kwargs={'remote_job_id' : latest_job.pk,
                                                         'instrument_name': instrument_name_lowercase })
        try:
            run_id = int(data_dict['data_file'])
            data_dict['webmon_url'] = "https://monitor.sns.gov/report/%s/%s/" %(instrument_name,run_id)
        except:
            pass
        reductions.append(data_dict)
        
    # Get all user configurations
    config_list = ReductionConfiguration.objects.filter(owner=request.user,
                                                        experiments=experiment_obj).order_by('name')
    configurations = []
    for item in config_list:
        data_dict = item.get_data_dict()
        data_dict['id'] = item.id
        latest_jobs = RemoteJobSet.objects.filter(configuration=item)
        if len(latest_jobs) > 0:
            latest_job = latest_jobs.latest('id')
            data_dict['latest_job'] = latest_job.id
            # data_dict['latest_job'] = reverse('eqsans.views.configuration_query', args=[latest_job.id])
        configurations.append(data_dict)
    
    breadcrumbs = Breadcrumbs()
    breadcrumbs.append_reduction(instrument_name_lowercase)
    breadcrumbs.append(ipts.lower())
    
    template_values = {'reductions': reductions,
                       'configurations': configurations,
                       'title': '%s %s' % (instrument_name_capitals, ipts),
                       'breadcrumbs': breadcrumbs,
                       'ipts_number': ipts,
                       'back_url': reverse('reduction_experiment', kwargs={'ipts' : ipts, 'instrument_name': instrument_name_lowercase }),
                       'icat_info': icat_ipts,
                       'form': reduction_start_form,
                       'is_categorized': not IS_UNCATEGORIZED,
                       'instrument' : instrument_name_lowercase, }
    if 'icat_error' in icat_ipts:
        template_values['user_alert'] = [icat_ipts['icat_error']]
    template_values = reduction_server.view_util.fill_template_values(request, **template_values)
#     logger.debug(pprint.pformat(configurations))
#     logger.debug(pprint.pformat(reductions))
    logger.debug(pprint.pformat(template_values))
    return render_to_response('%s/experiment.html' % instrument_name_lowercase,
                              template_values,
                              context_instance=RequestContext(request))
Example #5
0
def configuration_options(request, instrument_name, config_id=None):
    """
        Show the reduction properties for a given configuration,
        along with all the reduction jobs associated with it.
        Called when clicked Reduce->Batch Button, or new configuration
        
        @param request: The request object
        @param config_id: The ReductionConfiguration pk
    """
    
    logger.debug("configuration_options: %s"%inspect.stack()[0][3])
#     logger.debug("************************** POST")
#     l = request.POST.items()
#     l.sort()
#     logger.debug(pprint.pformat(l))
#     logger.debug("************************** GET")
#     l = request.GET.items()
#     l.sort()
#     logger.debug(pprint.pformat(l))
            
    instrument_name_capitals = str(instrument_name).upper()
    instrument_name_lowercase = str(instrument_name).lower()
    instrument_forms = view_util.import_module_from_app(instrument_name_lowercase,'forms')
    
    template_values = {}
    forms_handler = instrument_forms.ConfigurationFormHandler(request,config_id)
    
    # The list of relevant experiments will be displayed on the page
    expt_list = None
    job_list = None

    # Deal with data submission
    if request.method == 'POST':
        if forms_handler.are_forms_valid():
            config_id = forms_handler.save_forms()
            if config_id is not None:
                return redirect(reverse('configuration_options',
                                        kwargs={'config_id' : config_id,
                                                'instrument_name' : instrument_name_lowercase}))
    else:
        # Deal with the case of creating a new configuration
        if config_id is not None:
            reduction_config = get_object_or_404(ReductionConfiguration, pk=config_id, owner=request.user)
            expt_list = reduction_config.experiments.all()
            job_list = RemoteJobSet.objects.filter(configuration=reduction_config)

    breadcrumbs = Breadcrumbs()
    breadcrumbs.append_reduction(instrument_name_lowercase)
    if config_id is not None:
        breadcrumbs.append("configuration %s" % config_id)
    else:
        breadcrumbs.append("new configuration")

    # ICAT info url
    icat_url = reverse('catalog_run_info', args=[instrument_name_capitals, '0000'])
    icat_url = icat_url.replace('/0000', '')
    # TODO: add New an Save-As functionality
    template_values.update({'config_id': config_id,
                       'expt_list': expt_list,
                       'existing_job_sets': job_list,
                       'title': '%s Reduction' % instrument_name_capitals,
                       'breadcrumbs': breadcrumbs,
                       'icat_url': icat_url,
                       'instrument' : instrument_name, })
    
    template_values.update( forms_handler.get_forms())
    template_values = reduction_server.view_util.fill_template_values(request, **template_values)
    
    logger.debug(pprint.pformat(template_values))
    return render_to_response('%s/configuration_options.html' % instrument_name_lowercase,
                              template_values, context_instance=RequestContext(request))
Example #6
0
def reduction_options(request, reduction_id=None, instrument_name=None):
    """
        Display the reduction options form:
        
        If reduction_id exists, it will populate the form with information from that reduction.
            
        @param request: request object
        @param reduction_id: pk of reduction process object
    """
    
    logger.debug("Reduction: %s instrument_name=%s"%(inspect.stack()[0][3],instrument_name))
    
    instrument_name_capitals = str.capitalize(str(instrument_name))
    instrument_name_lowercase = str.lower(str(instrument_name))
    instrument_forms = view_util.import_module_from_app(instrument_name_lowercase,'forms')
    
    template_values = {}
    # Get reduction and configuration information
    config_obj = None
    if reduction_id is not None:
        reduction_proc = get_object_or_404(ReductionProcess, pk=reduction_id, owner=request.user)
        config_obj = reduction_proc.get_config()
    
    if request.method == 'POST':
        #logger.debug(pprint.pformat(request.POST.items()))
        
        options_form = instrument_forms.ReductionOptions(request.POST)
        # If the form is valid update or create an entry for it (if the data_file is different, a new entry is created!)
        if options_form.is_valid():
            new_reduction_id = options_form.to_db(request.user, reduction_id)
            if new_reduction_id is not None:
                messages.add_message(request, messages.SUCCESS, "Reduction parameters were sucessfully updated: " +
                "old_reduction_id=%s :: new_reduction_id=%s"%(reduction_id,new_reduction_id) )
                ## Keep the new reduction attached to the same configuration of the old one!
                # This is used for SEQ.
                # TODO: Check if SANS guys want that!
                if config_obj is not None:
                    reduction_proc = get_object_or_404(ReductionProcess, pk=new_reduction_id, owner=request.user)
                    config_obj.reductions.add(reduction_proc)
                    config_obj.save()
                return redirect(reverse('reduction_options',
                                        kwargs={'reduction_id' : new_reduction_id, 'instrument_name' : instrument_name}))
        else:
            messages.add_message(request, messages.ERROR, "The form is not valid. See errors above.")
    else:
        if reduction_id is not None:
            initial_values = instrument_forms.ReductionOptions.data_from_db(request.user, reduction_id)
        else:
            initial_values = copy.deepcopy(request.GET)
            if 'expt_name' in request.GET:
                initial_values['experiment'] = request.GET['expt_name']
        options_form = instrument_forms.ReductionOptions(initial=initial_values)
    
    breadcrumbs = Breadcrumbs()
    breadcrumbs.append_reduction(instrument_name_lowercase)
    
    if config_obj is not None:
        breadcrumbs.append_configuration(instrument_name_lowercase,config_obj.id)
        template_values.update({"properties":config_obj.get_data_dict()});
    if reduction_id is not None:
        breadcrumbs.append("reduction %s" % reduction_id)
    else:
        breadcrumbs.append("new reduction")

    # ICAT info url
    icat_url = reverse('catalog_run_info', args=[instrument_name_capitals, '0000'])
    icat_url = icat_url.replace('/0000', '')
    # TODO: add New an Save-As functionality
    template_values.update({'options_form': options_form,
                       'title': '%s Reduction' % instrument_name_capitals,
                       'breadcrumbs': breadcrumbs,
                       'reduction_id': reduction_id,
                       'icat_url': icat_url,
                       'instrument' : instrument_name_lowercase, })
    # Get existing jobs for this reduction
    if reduction_id is not None:
        existing_jobs = RemoteJob.objects.filter(reduction=reduction_proc)
        if len(existing_jobs) > 0:
            template_values['existing_jobs'] = existing_jobs.order_by('id')
        template_values['expt_list'] = reduction_proc.experiments.all()

    template_values = reduction_server.view_util.fill_template_values(request, **template_values)
    logger.debug(pprint.pformat(template_values))
    return render_to_response('%s/reduction_options.html' % instrument_name_lowercase,
                              template_values,context_instance=RequestContext(request))