def create_raw_report_from_data(report, data):
    """
    Create a raw report using data and report metadata.

    Parameters
    ----------
    report : :py:class:`solarforecastarbiter.datamodel.Report`
        Metadata describing report
    data : dict
        Keys are all Forecast and Observation (or Aggregate)
        objects in the report, values are the corresponding data.

    Returns
    -------
    raw_report : :py:class:`solarforecastarbiterdatamodel.RawReport`

    Todo
    ----
    * add reference forecast
    """
    generated_at = pd.Timestamp.now(tz='UTC')
    report_params = report.report_parameters
    timezone = infer_timezone(report_params)
    versions = get_versions()
    with hijack_loggers([
        'solarforecastarbiter.metrics',
        'solarforecastarbiter.reports.figures.plotly_figures'],
                        ) as handler:
        # Validate, fill forecast, and resample
        processed_fxobs = preprocessing.process_forecast_observations(
            report_params.object_pairs,
            report_params.filters,
            report_params.forecast_fill_method,
            report_params.start, report_params.end,
            data, timezone,
            costs=report_params.costs)

        # Calculate metrics
        metrics_list = calculator.calculate_metrics(
            processed_fxobs,
            list(report_params.categories),
            list(report_params.metrics))
        summary_stats = calculator.calculate_all_summary_statistics(
            processed_fxobs, list(report_params.categories))

        report_plots = plotly_figures.raw_report_plots(report, metrics_list)
        messages = handler.export_records()
    raw_report = datamodel.RawReport(
        generated_at=generated_at, timezone=timezone, versions=versions,
        plots=report_plots, metrics=tuple(metrics_list + summary_stats),
        processed_forecasts_observations=tuple(processed_fxobs),
        messages=messages)
    return raw_report
 def wrapper(*args, **kwargs):
     try:
         out = f(*args, **kwargs)
     except Exception:
         msg = datamodel.ReportMessage(
             message=err_msg,
             step='solarforecastarbiter.reports.main',
             level='CRITICAL',
             function=str(f)
         )
         raw = datamodel.RawReport(
             pd.Timestamp.now(tz='UTC'), 'UTC', (), None,
             (), (), (msg,))
         session.post_raw_report(report_id, raw, 'failed')
         raise
     else:
         return out
示例#3
0
def test_render_pdf_special_chars(
        ac_power_observation_metadata, ac_power_forecast_metadata, dash_url,
        fail_pdf, preprocessing_result_types, report_metrics):
    if shutil.which('pdflatex') is None:  # pragma: no cover
        pytest.skip('pdflatex must be on PATH to generate PDF reports')
    quality_flag_filter = datamodel.QualityFlagFilter(
        (
            "USER FLAGGED",
        )
    )
    forecast = ac_power_forecast_metadata.replace(
        name="ac_power forecast (why,)  ()'-_,")
    observation = ac_power_observation_metadata.replace(
        name="ac_power observations  ()'-_,")
    fxobs = datamodel.ForecastObservation(forecast,
                                          observation)
    tz = 'America/Phoenix'
    start = pd.Timestamp('20190401 0000', tz=tz)
    end = pd.Timestamp('20190404 2359', tz=tz)
    report_params = datamodel.ReportParameters(
        name="NREL MIDC OASIS GHI Forecast Analysis  ()'-_,",
        start=start,
        end=end,
        object_pairs=(fxobs,),
        metrics=("mae", "rmse", "mbe", "s"),
        categories=("total", "date", "hour"),
        filters=(quality_flag_filter,)
    )
    report = datamodel.Report(
        report_id="56c67770-9832-11e9-a535-f4939feddd83",
        report_parameters=report_params
    )
    qflags = list(
        f.quality_flags for f in report.report_parameters.filters if
        isinstance(f, datamodel.QualityFlagFilter)
    )
    qflags = list(qflags[0])
    ser_index = pd.date_range(
        start, end,
        freq=to_offset(forecast.interval_length),
        name='timestamp')
    ser = pd.Series(
        np.repeat(100, len(ser_index)), name='value',
        index=ser_index)
    pfxobs = datamodel.ProcessedForecastObservation(
        forecast.name,
        fxobs,
        forecast.interval_value_type,
        forecast.interval_length,
        forecast.interval_label,
        valid_point_count=len(ser),
        validation_results=tuple(datamodel.ValidationResult(
            flag=f, count=0) for f in qflags),
        preprocessing_results=tuple(datamodel.PreprocessingResult(
            name=t, count=0) for t in preprocessing_result_types),
        forecast_values=ser,
        observation_values=ser
    )

    figs = datamodel.RawReportPlots(
        (
            datamodel.PlotlyReportFigure.from_dict(
                {
                    'name': 'mae tucson ac_power',
                    'spec': '{"data":[{"x":[1],"y":[1],"type":"bar"}]}',
                    'pdf': fail_pdf,
                    'figure_type': 'bar',
                    'category': 'total',
                    'metric': 'mae',
                    'figure_class': 'plotly',
                }
            ),), '4.5.3',
    )
    raw = datamodel.RawReport(
        generated_at=report.report_parameters.end,
        timezone=tz,
        plots=figs,
        metrics=report_metrics(report),
        processed_forecasts_observations=(pfxobs,),
        versions=(('test',  'test_with_underscore?'),),
        messages=(datamodel.ReportMessage(
            message="Failed to make metrics for ac_power forecast ()'-_,",
            step='', level='', function=''),))
    rr = report.replace(raw_report=raw)
    rendered = template.render_pdf(rr, dash_url)
    assert rendered.startswith(b'%PDF')