Skip to content

Commit b0d29f5

Browse files
wfviningwfvining-snlcwhansewholmgrenAzizCode92
authored
Support for PV systems with multiple arrays (#1076)
* Initial implementation of pvsystem.Array class Provides the three basic methods that depend on tilt and azimuth and provides a container for other parameters which may vary from array to array but do not vary within a single array (racking, temperature model params, albedo, strings, modules per string, etc.). * Refactor PVSystem to use pvsystem.Array internally Removes array-related fields and adds _array field. All internal references to array-related attributes now refer to the the corresponding attributes of the Array class. It is likely some of the Array attributes will need to be exposed on the PVSystem instances via @properties; however, any of these instances are not covered by tests so it will be necessary to carefully work through the other places where PVsystem is used (ModelChain and child classes) to see what needs to be done. * Use self._array.temperature_parameters in PVSystem Use the temperature model parameters from the Array instance inside PVSystem. Also properly initialize the parameters. * Fix error passing surface_tilt in place of surface_azimuth Mistake in invocation of Array.__init__() in PVSystem.__init__() * Expose Array attributes as attributes of PVSystem Uses `@property` to provide getters and setters for Array attributes in order to mimic the original behavior of the PVSystem class. * Pass attributes of PVSystem._array when constructing LocalizedPVSystem * Fix over-indented lines * Access Array attributes as attributes of the PVSystem Since the Array attributes are all exposed via @propertys on PVSystem, we can access them directly, reducing the number of changes needed to add the Array class. * Initialize Array.albedo correctly * add ModelChainResults, plumb for airmass * assign rest of ModelChain outputs to ModelChain.results * first cut at ModelChain tests * formatting * more test development * few more additions * put dataclasses in pip section for py36 * Store a list of Arrays in PVSystem Adds the @singleton_as_scalar decorator to make a PVSystem with a single Array appear unchanged from the original PVSystem implementation. * Wrap per-array inputs in a list Adds a decorator (@list_or_scalar) used to specify which parameters should be lists of the same length as PVSystem._arrays. The decorator handles validation by transforming non-list values to singleton lists then comparing to the length of the _arrays field on the PVSystem instance passed as the first parameter. Needs tests with multiple Arrays, but must wait until we have an API for adding multiple Arrays to a PVSystem. * Restore PVSystem._infer_cell_type() This function is used in the test suite. It may not be needed otherwise, but to move forward without needing to rewrite the tests I'm adding it back to the PVSystem class as a wrapper around Array._infer_cell_type() * Rename and document validation decorator Renames `@list_or_scalar` to `@validate_against_arrays` and add a docstring describing its behavior. * Rename decorator for returning singleton list as a single value Update docstring to make behavior more clear. * Fix indentation and formatting errors * Use nested def instead of assigning a lambda Instead of assigning a lambda expression use an internal def to define function for building the pvsyst_celltemp kwargs. * Fix indentation in ModelChain._prepare_temperatures * Add test for Array.__repr__() * Pass list of Arrays to PVSystem.__init__ To construct a PVSystem instance with multiple arrays users can pass a list of Array instances. * Return tuple instead of list for multi-array PVSystem Change the representation of PVSystem._array to a tuple as well. * Fix indentation * deprecate old ModelChain attributes * remove solar_position = None from ModelChain.__init__ * Require tuple input in list_or_scalar decorator After change to returning tuple as lists we need to update the decortor to check for the correct type. It is tempting to test for any Iterable here; however, since some of the parameters are tuples of Series or DataFrame (which are themselves iterabel), we need to be careful. I believe the best option is to be very restrictive and expect input to be a tuple. * Document meaning of `arrays` parameter to PVSystem.__init__ * Test multi-array PVSystem.scale_voltage_current_power() * add modelchain test on pvsystem with 2 arrays * Test multi-array PVSystem.get_aoi() * Test multi-array PVSystem.get_irradiance() Just test that PVSystem.get_irradiance returns a tuple that has the irradiance for each array, test_PVSystem_get_irradiance() suffices to test the the value returned by Array.get_irradiance() is correct. * Test multi-array PVSystem.pvwatts_dc() * Test input length validation on PVSystem.pvwatts_dc() * Cover non-tuple iterable edge case Per-Array input must be passed as a tuple, arbitrary iterable will raise a ValueError even if the length is correct. * Test multi-array PVSystem.get_iam() * Fix whitespace in test_pvsystem.py * Test PVSystem.get_iam() input length mismatch * Test PVSystem.sapm with multiple arrays * Test PVSystem.sapm_spectral_loss with multiple arrays * Test PVSystem.sapm_effective_irradiance with multiple arrays * Test PVSystem.sapm_celltemp() with multiple arrays * Clean up whitespace * Test PVSystem.first_solar_spectral_loss() with multiple arrays * Test PVSystem.pvsyst_celltemp() with multiple arrays Add two_array_system fixture to reduce duplicate setup code. * Consolidate tests for PVSystem.xxxx_celltemp() functions These all follow a similar pattern, so we can consolidate into two tests patrametrized by a list of the celltemp functions to test. * Clean up whitespace * Fix comment in PVSystem.fuentes_celltemp() Now we get the surface_tilt attribute form the Array, not PVSystem * Test all PVSystem.calcparams_xxxx() functions with multiple arrays * Add tests to cover PVSystem.albedo and PVSystem.surface_azimuth attributes * Conditionally install dataclasses for tests * formatting * Remove TODOs * Make decorators private These decorators are not intended to be used anywhere else. Also rename to avoid 'singleton' which is not being used in the standard "singleton design pattern" sense. * Update PVSystem.__repr__() to handle multiple Arrays * Expect new format in tracking.SingleAxisTracker.__repr__() tests Format has changed to support multi-array PVSystems. * Update parameter names and doc for _validate_against_arrays() * Replace validation decorator with a private method The decorator adds too much complexity and room for error in the future. A validation method that is called once on each parameter that needs to be the same shape as the `self._arrays` tuple is much easier to read, understand, and maintain. It also has the benefit of increased flexibility since it allow validation to be triggered at any point, rather than before the method is called. * Remove unused `inspect` import in `pvsystem` * Add blank line before nested defs * lets see what breaks * correct misspelled parameters * infer methods, handle tuples in calculations * inverter isn't on array * fix iteration in ModelChain.effective_irradiance_model * _tuple_from_dfs to function * use isinstance for dataframe vs. tuple of df * consolidate check for consistent parameters * missing set() * missed one instance * Rename and document kwarg to prevent unwrapping return value * Test ModelChain with multi-array system and no losses Add a test that verifies the dc side of the ModelChain returns the correct data for each Array with `aoi_model='no_loss'` and `spectral_model='no_loss'`. Test fails because `ModelChain.results.spectral_modifier` and `ModelChain.results.aoi_modifier` are assigned a scalar value instead of a tuple. It is very likely we will also see a failure at the `ModelChain.losses_model()` call in `_run_from_effective_irradiance()` for the same reason. At this point we should (maybe) expect a failure at the call to `ModelChain.ac_model()` since we have not implemented an inverter model for multiple arrays yet. * Initialize losses parameters corresponding to system._arrays In the no_losses case, loss parameters are initialized to 1. This commit initializes a tuple with the same number of elements as the number of arrays in the system. In cases where losses are being modeled, these fields are initialized to the result of a PVSystem method call, meaning they have the correct type and shape. For cases with no losses we need to take care to manually initialize them correctly. After this commit test_run_model_from_irradiance_arrays_no_loss() fails at the call to PVSystem.pvwatts_ac() which is expected since we have not implemented inverter models with multiple DC inputs yet. * Fix whitespace * Add PVSystem.num_arrays property * Use self.system.num_arrays instead of len(self.system._arrays) * Correct types of ModelChainResult fields Declares a PerArray type which is either a single value or a tuple of many values with the same type. The type for every field that should have the same length as the number of arrays is .Optional[PerArray[X]] * Remove direct uses of ModelChain.system._arrays Preserve encapsulation. Add an function _array_keys() that is similar to _tuple_from_dfs in order to transparently handle the different types returned by PVSystem attributes. * Assign to self.results.effective_irradiance Don't assign to the deprecated self.effective_irradiance field internally. * Test multi-array ModelChain with pvwatts losses * Shorten line * Test multi-array modelchain with DC models that call _singlediode * Rewrite ModelChain._singlediode to support multi-array systems Slightly different logic depending on the number of arrays. This could be done a little more cleanly with the `unwrap=False` kwarg to `calcparams_model_function` and `system.scale_voltage_current_power`. That would give us a consistent type to work with, requiring only one if statement to unwrap dc power ourselves if `system.num_arrays == 1`; however, `mocker.spy` attempts to bind unwrap explicitly resulting in a test failure where there should not be one, since unwrap is an extra, non-explicit, parameter added by the `_unwrap_single_value` decorator. * Add `name` attribute to `pvsystem.Array` It may be useful to refer to Arrays by name in the future. Adds an optional field to the Array class to support this. * Allow per-array GHI/DHI/DNI input to PVSystem.get_irradiance() * Test that the correct input is passed to each array Validates the output of PVSystem.get_irradiance() by checking against the output from Array.get_irradiance() with the expected input for each Array. * Fix whitespace in test_modelchain.py * Support multiple weather input to PVSystem.xxxx_celltemp() Support for system-wide or per-array values of air temperature and wind speed. * Fix whitespace in test_pvsystem.py In tests: - test_PVSystem_multi_array_celltemp_wind_too_long() - test_PVSystem_multi_array_celltemp_temp_too_long() * Allow unique weather input for each array Updates ModelChain.prepare_inputs() to accept either a tuple of DataFrames or a single DataFrame. If `weather` is a tuple each DataFrame it contains must have the same index and must have all of the required columns ('ghi', 'dhi', 'dni'). * Document that ModelChain.prepare_inputs() can take a tuple Expand docstring to include new parameter type and note on the exceptions that can be raised. * Raise if length of weather is not same as system.num_arrays Rather than raising the exception from deep in PVSystem we test the length and raise immediately to make the error easier to understand and debug for users. * Add tests for ModelChain.run_model with multiple weather * Add test for ModelChain._prepare_temperature with multiple weather * Use itertools.starmap in _validate_weather_indices Substantially more readable and concise. * Update arrays in sapm_dc_snl_ac_system_same_arrays fixture Use the sam array parameters as sapm_dc_snl_ac so we can use the same expected output in multi-array tests. * Rework _prepare_temperature tests Add some assertions to verify that the cell temperature for both arrays is not the same. * ModelChain._prepare_temperature accepts multiple DataFrames If multiple dataframes are passed in a tuple then _prepare_temperature will look for 'cell_temperature' or 'module_temperature' in each data frame. For data frames that do not have one of these columns the ModelChain.temperature_model() is applied to calculate the cell temperature from the weather data that has already been assigned in other ModelChain fields. * Fix indentation in ModelChain._get_cell_temperature() * Support multiple weather DataFrames in all ModelChain.xxxx_temp() Adds support for per-array weather input in - ModelChain.pvsyst_temp() - ModelChain.faiman_temp() - ModelChain.fuentes_temp() Support was added in ModelChain.sapm_temp() in a previous commit. * Refactor ModelChain.xxxx_temp() functions Abstract the pattern used in each function to reduce code duplication. Should reduce the burden for adding new temperature models as well as maintenance in the future. * Accept multiple weather frames in ModelChain.complete_irradiance Apply the same logic as in ModelChain.prepare_inputs to validate the indices of the data frames. Iterate over them, adding missing columns where necessary. * ModelChain.complete_irradiance input same length as number of arrays Document the new input types and exceptions. * Validate per-array input to ModelChain.prepare_inputs_from_poa() When passing POA irradiance directly to ModelChain, it must be passed independently for each array. If the wrong number of POA dataframes are provided by the user we raise a value error. * Multiple inputs to ModelChain.run_model_from_effective_irradiance() Multi-array systems require multiple effective irradiance DataFrames. * Clean up whitespace * Only validate indices if a tuple is passed * Add test to cover undefined attribute Because we hook `__getattr__` in order to deprecate the old results attributes (e.g. `ModelChain.dc`) we need to test that an AttributeError is raised when an unknown attribute is requested. * Verify all arrays have consistent parameters Cliff wrote this. This commit just invokes the method and updates it so it works with only one array. * Don't test that all combinations of indices are equal Because we are just comparing for equality we can infer from a == b and b == c that a == c and don't have to explicitly check every combination. * Use ModelChain.results.dc instead of ModelChain.dc ModelChain.dc will be deprecated when this is merged. * Consolidate multi-input validation Perform all validation for multi-array/multi-weather input in a single method, `ModelChain._check_multiple_input()`. * Add tests for multi-array module/string paramters Tests PVSystem.modules_per_string and PVSystem.strings_per_inverter. * Refactor all same index check * Prevent instantiation of SingleAxisTracker with multiple arrays Supporting tracking systems with multiple Arrays is a can of worms that we don't want to open right now. Until support can be added we will raise a ValueError if a user tries to instantiate a tracking system with multiple arrays. * Test that inconsistent array parameters causes error If given a multi-array PVSystem where arrays have inconsistent module or temperature model parameters a ValueError should be raised. * Add test coverage for pvsystem.Array._infer_xxxx() methods * Add pvsystem.Array to Classes section of api.rst * Add PVSystem.sandia_multi() method Adds a wrapper for the `pvlib.inverter.sandia_multi` inverter model to PVSystem. * Fix whitespace * Add 'sandia_multi' as a valid key for ModelChain.ac_model Adds the ModelChain.sandia_multi_inverter() method which calls PVSystem.sandia_multi to set ModelChain.results.ac. * Add sandia_multi_inverter to ModelChain.infer_ac_model() Since no other inverter models currently support multiple dc inputs we raise a value error whenever the system has more than one array and is missing the inverter parameters required for sandia_multi_inverter. * Update ModelChain tests to use sandia_multi inverter model * Shorten long line * Support multiple arrays in ModelChain.pvwatts_losses * Decorate test_complete_irradiance_arrays with @requires_tables * Pass explicit freq to DataFrame.shift() in poa_arrays test * Pass explicit freq to DataFrame.shift() in ModelChain tests In test_run_model_from_effective_irradiance_arrays_error() A different index is generated by shifting the original input. Later versions of pandas support freq='infer', but not the minimum supported version for pvlib. * Add description of multi-array PVSystem to pvsystem.rst * Remove commented-out code in ModelChainResults * Docstring edits * Remove stray whitespace from _tuple_from_dfs() docstring * Add docstring to ModelChain._check_consistent_params() * Improvements in pvsystem.rst Co-authored-by: Cliff Hansen <[email protected]> * Docstring edits in pvsystem.py Co-authored-by: Cliff Hansen <[email protected]> * Shorten line in pvsystem.Array docstring * Fix typo in ModelChain.complete_irradiance() docstring Co-authored-by: Will Holmgren <[email protected]> * Avoid use of `inplace=True` in ModelChain._singlediode() * Make list of deprecated ModelChain attrs a class variable * Include 'dataclasses' as a requirement in setup.py Only included if python version is 3.6 since dataclasses is part of the standard library for 3.7+. * Remove dataclasses from CI environment for python 3.7+ * Replace modelchain._array_keys() with modelchain._common_keys() _array_keys() just returned the keys of one specific array, what we actually need is to return the set of keys that are common to every dict in a tuple. * Update ModelChain.__getattr__ deprecation message Note that the deprecated attributes will be removed in 0.10, not 1.0. * Expose PVSystem.arrays as a public attribute This attribute holds the tuple of arrays in the PVSystem. * Iterate over arrays in ModelChain._check_consistent_params() Rather than iterating over individual parameters for each Array we iterate over the arrays. Effectively the same, but much more readable. * Refactor ModelChain.effective_irradiance_model() Reduce code duplication by calling nested def for the single-array case. * rewrite pvsystem.rst * Raise a TypeError in ModelChain._check_multiple_input() When input must be a tuple, we should raise a TypeError, rather than a ValueError. * Note that indices assumed to be same in ModelChain._assign_times() * Add comment in ModelChain.complete_irradiance() Note why `ModelChain._assign_weather()` is not used here. * Copy input before assigning in ModelChain.complete_irradiance() To ensure that input data is not modified copy the data frames that are passed to ModelChain.complete_irradiance() before assigning `ModelChain.weather`. * Document ModelChain.run_model() and run_model_from_poa() input type Expand docstring to describe tuple input where each element specifies the input for the corresponding Array. * Don't allow SingleAxisTracker Array with non-None tilt/azimuth If a list of one Array is given a value error is raised when it has non-None tilt or azimuth. Rather than just assigning None we raise an error so that the Array object itself is not modified (since it could be in use by the user somewhere else). When only parameters are passed (as opposed to an Array object) we override the values. Since the Array is created internally and we know it is not in use elsewhere this isn't a problem. * Improve documentation of ValueErrors from ModelChain methods Readability improvements by breaking up multiple reasons for a value error into separate items. * Separate ac model inference for multiple arrays Adds an internal _infer_ac_model_multi() method to handle inference when system.num_arrays > 1. This lets us raise a more usefule error message in this case. In addition several _xxxx_params() predicates are added to prevent duplication of the specific tests on the inverter_params set in _infer_ac_model_multi(). Seems like over-kill for now, but an inverter.pvwatts_multi() model is in the works, so this will save some work when integrating that. * Update docstring for ModelChain.run_model_from_effective_irradiance() Was referring to ModelChain.run_model_from() in the "See also" section. That doesn't exist; changed to ModelChain.run_model() Co-authored-by: Will Holmgren <[email protected]> * Expand error messages for missing array params in ModelChain Note that all Arrays must have the correct/required model parameters when an error is raised for missing parameters related to the inference or assignment of the various models used in an instance of ModelChain. * Remove ModelChain._check_consistent_params Rework test to maintain coverage on inconsistent array parameters, but expect the error to come from a different place. Mainly this means that the error message has changed and more input is needed to the constructor to make sure that execution goes all the way to the assignment of the temperature model. * Test ModelChain.infer_ac_model() error with one array Make sure that an error is raised for a model chain with a single- array system and invalid inverter_params. * Capitalize 'Arrays' when referring to the "constituents" of a PVSystem Apply consistent capitalization to make it clear when we are referring to the idea of an array or an Array instance in a PVSystem. * Return early from ModelChain._prepare_temperature() If all Arrays have a cell_temperature or module_temperature given in the input data then return early and don't try to compute cell temperature based on weather. This supports calling ModelChain.run_from_effective_irradiance() with only 'cell_temperature' and 'effective_irradiance' columns present in the input. * More test coverage of ModelChain.run_model_from_effective_irradiance() * Note poa_global requirements for run_model_from_effective_irradiance() Add not about when poa_global is required in the ModelChain.run_model_from_effective_irradiance() docstring. * Move ModelChain.tracking to ModelChain.results.tracking Add tracking to deprecated attribute list. * Improve pvsystem.Array docstring Note that Array represents an array at a 'fixed orientation' * Better documentation for ModelChain._check_multiple_input() Provides a more thorough and informative description of the `strict` parameter. * Raise ValueError from ModelChain._prepare_temperature() If the input data is missing cell_temperature for some Arrays then the input must specify poa_global for _all_ Arrays. * Update expected error message for run_model_from_effective_irradiance() * coerce weather/data to tuple in run_model methods * don't use decorator, _to_tuple in complete_irradiance * adjust modelchain, add tests for [weather, weather], add test_run_model_from_poa_arrays * Parameterize types in tests Co-authored-by: Will Vining <[email protected]> * add tuple/list type tests * Use unwrap=True to simplify ModelChain._singldiode() This lets us expect a consistent type from the `PVSystem` methods regardless of the number of arrays. Because of that we can remove the control-flow that made the function hard to read. This comes at the cost of needing to unwrap the single value ourselves before returning, but a single if statement at the end of the method is much easier to reason about. Because of the way mocks interact with wrapped functions we need to move the mock from the object layer to the function layer, or it will fail because the signature of the wrapped PVSystem methods does not include the `unwrap` parameter. * Add docstrings to helper functions * Fix type annotations in ModelChainResults Some fields had the wrong type (solar_position, airmass, ac, dc) * Add index information to error message in ModelChain._verify() Provide information to the caller about which input is missing a column. * fix copy, add input_type to wrong length tests * Improve error message for inconsistent temperature model params * Correct attribute name in ModelChain._set_celltemp docstring self.results.cell_temp -> self.results.cell_temperature * Remove unused ModelChainResult.array_ac field * add coerce to prepare_inputs functions * add _to_tuple back to run_model * Coerce weather/data inputs to tuple in ModelChain entry points (#1) * coerce weather/data to tuple in run_model methods * add tuple/list type tests * add input_type to wrong length tests * add coerce to prepare_inputs functions Co-authored-by: Will Vining <[email protected]> * Add DatetimeIndex for test_prepare_inputs_multi_weather() * Add whatsnew entries for 0.9.0 List of deprecated ModelChain attributes and brief summaries of the main API enhancements. * edits to pvsystem.rst * fix ipython in pvsystem.rst * edits to modelchain.py docstrings * minor edits to whatsnew * pvsystem.rst edits * Allow Series input to modelchain._common_keys() Return the intersection of the indices of the series. This supports the use case shown in introtutorial.rst where module parameters are a column selected from the a data frame. * Update whatsnew v0.9.0 label * Note dataclasses requirement in whatsnew/v0.9.0.rst * Fix indentation in ModelChain.martin_ruiz_aoi_loss() * Clean up Array.get_iam() docstring Change PVSystem.module_parameters to Array.module_parameters. Fix indentation of Raises section * Change PVSystem to Array in Array.get_iam() error message * Update links to other pvlib functions in Array.get_irradiance() Links in docstring were broken. Use full name to fix. * Compare function objects in ModelChain._get_cell_temperature() Rather than using the name of the function we can compare directly to the ModelChain.sapm_temp() bound method to check whether the sapm temperature model is in use. * merge master, edits to pvsystem.rst from review * Reword multi-array SingleAxisTracker error message remove the word "currently" * Revert "Compare function objects in ModelChain._get_cell_temperature()" This reverts commit 111ff32. Using `is` here was a mistake, and does not work. * Update return types of PVSystem methods Some methods now return tuples. * Compare function objects in ModelChain._get_cell_temperature() Rather than relying on the name of the function we can compare function objects directly to determine if the sapm_temp model has been selected by the user. * Add project urls to setup.py for pypi page (#1119) * Update setup.py * Update setup.py * add project_urls * Update v0.8.1.rst * Update v0.8.1.rst * fix pvgis test (#1121) * make clean: also delete generated, auto_examples, savefig (#1122) * merge master, edits to pvsystem.rst from review * Fix formatting in PVSystem.get_iam() docstring * Pass model and kwargs to Array.get_irradiance() Fixes bug where the `model` param and keyword arguments were not passed when PVSystem.get_irradiance() called Array.get_irradiance() * Note which parameters of PVSystem methods accept tuples Add note to parameter type in docstrings. * Update Array docstring to describe modules "at same orientation" * Document 0.25 as fallback value for Array.albedo * Update defaults in Array docstring * Rename and clean up duplicate PVSystem test * Reword PVSystem.sandia_multi docstring * Add notes on system-wide parameters to PVSystem method docstrings * Add ModelChainResults to classes section of api.rst * Expand ModelChain docstring to describe how models are applied Make clear that the same model is applied to each array in the system. * Revert "Add ModelChainResults to classes section of api.rst" This reverts commit 68617fa. The current sphinx configuration can't handle this because ModelChainResult does not have an explicit __init__ method. This results in an OSError during the build when sphinx tries to make the source code pages. * Simplify ModelChain.__getattr__() Removes redundant look-up in self.__dict__ * Replace object with super() in ModelChain.__setattr__ * Use mc.results.ac instead of mc.ac in introtutorial.rst * Replace deprecated ModelChain attributes in forecasts.rst * fix pvsystem.rst examples * Fix bug in pvsystem.rst examples Forgot to pass module_parameters to PVSystem constructor. * Add modelchain.ModelChainResult to Classes section of api.rst Requires slight modification of sphinx/source/conf.py to address getting line numbers for the ModelChainResult.__init__ method which is not explicitly defined (and therefore does not have a line number). Made the T TypeVar private so it does not clutter the attribute list for ModelChainResult. Add docstring for the PerArray type. * Update contributors list Co-authored-by: Will Holmgren <[email protected]> * Add ModelChain.solar_position to deprecated attrs in whatsnew * Fix single array aoi example output was printing the wrong aoi * Add missing space in ValueError message from PVSystem.get_iam() * Add Results to ModelChain section of api.rst Co-authored-by: Will Vining <[email protected]> Co-authored-by: Cliff Hansen <[email protected]> Co-authored-by: Will Holmgren <[email protected]> Co-authored-by: Aziz <[email protected]> Co-authored-by: Kevin Anderson <[email protected]>
1 parent ba7d753 commit b0d29f5

15 files changed

+3236
-574
lines changed

ci/requirements-py36-min.yml

+1
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ dependencies:
1313
- pytz
1414
- requests
1515
- pip:
16+
- dataclasses
1617
- numpy==1.12.0
1718
- pandas==0.22.0
1819
- scipy==1.2.0

ci/requirements-py36.yml

+1
Original file line numberDiff line numberDiff line change
@@ -27,5 +27,6 @@ dependencies:
2727
- siphon # conda-forge
2828
- statsmodels
2929
- pip:
30+
- dataclasses
3031
- nrel-pysam>=2.0
3132
- pvfactors==1.4.1

docs/sphinx/source/api.rst

+8-1
Original file line numberDiff line numberDiff line change
@@ -20,9 +20,10 @@ corresponding procedural code.
2020

2121
location.Location
2222
pvsystem.PVSystem
23+
pvsystem.Array
2324
tracking.SingleAxisTracker
2425
modelchain.ModelChain
25-
26+
modelchain.ModelChainResult
2627

2728
Solar Position
2829
==============
@@ -583,6 +584,12 @@ Functions to assist with setting up ModelChains to run
583584
modelchain.ModelChain.prepare_inputs
584585
modelchain.ModelChain.prepare_inputs_from_poa
585586

587+
Results
588+
-------
589+
590+
Output from the running the ModelChain is stored in the
591+
:py:attr:`modelchain.ModelChain.results` attribute. For more
592+
information see :py:class:`modelchain.ModelChainResult`.
586593

587594
Attributes
588595
----------

docs/sphinx/source/conf.py

+4
Original file line numberDiff line numberDiff line change
@@ -388,6 +388,10 @@ def get_linenos(obj):
388388
lines, start = inspect.getsourcelines(obj)
389389
except TypeError: # obj is an attribute or None
390390
return None, None
391+
except OSError: # obj listing cannot be found
392+
# This happens for methods that are not explicitly defined
393+
# such as the __init__ method for a dataclass
394+
return None, None
391395
else:
392396
return start, start + len(lines) - 1
393397

docs/sphinx/source/forecasts.rst

+3-3
Original file line numberDiff line numberDiff line change
@@ -471,7 +471,7 @@ Here's the forecast plane of array irradiance...
471471

472472
.. ipython:: python
473473
474-
mc.total_irrad.plot();
474+
mc.results.total_irrad.plot();
475475
@savefig poa_irrad.png width=6in
476476
plt.ylabel('Plane of array irradiance ($W/m^2$)');
477477
plt.legend(loc='best');
@@ -482,7 +482,7 @@ Here's the forecast plane of array irradiance...
482482

483483
.. ipython:: python
484484
485-
mc.cell_temperature.plot();
485+
mc.results.cell_temperature.plot();
486486
@savefig pv_temps.png width=6in
487487
plt.ylabel('Cell Temperature (C)');
488488
@suppress
@@ -492,7 +492,7 @@ Here's the forecast plane of array irradiance...
492492

493493
.. ipython:: python
494494
495-
mc.ac.fillna(0).plot();
495+
mc.results.ac.fillna(0).plot();
496496
plt.ylim(0, None);
497497
@savefig ac_power.png width=6in
498498
plt.ylabel('AC Power (W)');

docs/sphinx/source/introtutorial.rst

+1-1
Original file line numberDiff line numberDiff line change
@@ -165,7 +165,7 @@ by examining the parameters defined for the module.
165165
# model results (ac, dc) and intermediates (aoi, temps, etc.)
166166
# assigned as mc object attributes
167167
mc.run_model(weather)
168-
annual_energy = mc.ac.sum()
168+
annual_energy = mc.results.ac.sum()
169169
energies[name] = annual_energy
170170
171171
energies = pd.Series(energies)

0 commit comments

Comments
 (0)