コード例 #1
0
        public static TimeSeriesDescription GetTimeSeriesDescription(this IAquariusClient client, string identifier)
        {
            var locationIdentifier = TimeSeriesIdentifierParser.ParseLocationIdentifier(identifier);

            var response = client.Publish.Get(new TimeSeriesDescriptionServiceRequest
            {
                LocationIdentifier = client.FindLocationDescription(locationIdentifier).Identifier
            });

            var caseInsensitiveMatches = response
                                         .TimeSeriesDescriptions
                                         .Where(t => t.Identifier.Equals(identifier, StringComparison.InvariantCultureIgnoreCase))
                                         .ToList();

            if (!caseInsensitiveMatches.Any())
            {
                throw new ExpectedException($"Can't find '{identifier}' at location '{locationIdentifier}'");
            }

            if (caseInsensitiveMatches.Count == 1)
            {
                return(caseInsensitiveMatches.Single());
            }

            var exactMatch = caseInsensitiveMatches
                             .FirstOrDefault(t => t.Identifier == identifier);

            if (exactMatch != null)
            {
                return(exactMatch);
            }

            throw new ExpectedException($"{caseInsensitiveMatches.Count} ambiguous matches for '{identifier}': {string.Join(", ", caseInsensitiveMatches.Select(t => t.Identifier))}");
        }
コード例 #2
0
        private List <ReflectedTimeSeriesPoint> LoadPointsFromNg(IAquariusClient client)
        {
            var timeSeriesInfo = client.GetTimeSeriesInfo(Context.SourceTimeSeries.Identifier);

            var points = client.Publish.Get(new TimeAlignedDataServiceRequest
            {
                TimeSeriesUniqueIds = new List <Guid> {
                    timeSeriesInfo.UniqueId
                },
                QueryFrom = Context.SourceQueryFrom?.ToDateTimeOffset(),
                QueryTo   = Context.SourceQueryTo?.ToDateTimeOffset()
            })
                         .Points
                         .Select(p => new ReflectedTimeSeriesPoint
            {
                Time       = Instant.FromDateTimeOffset(p.Timestamp),
                Value      = p.NumericValue1,
                GradeCode  = p.GradeCode1.HasValue ? (int)p.GradeCode1 : (int?)null,
                Qualifiers = QualifiersParser.Parse(p.Qualifiers1)
            })
                         .ToList();

            Log.Info($"Loaded {points.Count} points from {timeSeriesInfo.Identifier}");

            return(points);
        }
コード例 #3
0
 public static TimeSeries GetTimeSeriesInfo(this IAquariusClient client, string identifier)
 {
     return(client.Provisioning.Get(new GetTimeSeries
     {
         TimeSeriesUniqueId = GetTimeSeriesUniqueId(client, identifier)
     }));
 }
コード例 #4
0
        private void Connect()
        {
            try
            {
                _client = AquariusClient.CreateConnectedClient(
                    serverTextBox.Text.Trim(),
                    usernameTextBox.Text.Trim(),
                    passwordTextBox.Text.Trim());

                Info($"{Text} connected to AQTS {_client.ServerVersion} on {GetServerName()}");

                ValidateConnection();

                GetAllPlugins();

                CheckForMissingPlugins();

                connectButton.Enabled    = false;
                disconnectButton.Enabled = true;
                addButton.Enabled        = true;
                priorityUpButton.Enabled = priorityDownButton.Enabled = !IsPureApiVersion();
                serverTextBox.Enabled    = false;
                usernameTextBox.Enabled  = false;
                passwordTextBox.Enabled  = false;
            }
            catch (Exception exception)
            {
                Disconnect();
                Error(exception);
            }
        }
コード例 #5
0
ファイル: PointsAppender.cs プロジェクト: craignwf/examples
 private void ThrowIfGapsNotSupported(IAquariusClient client)
 {
     if (Points.Any(p => p.Type == PointType.Gap) && client.ServerVersion.IsLessThan(MinimumGapVersion))
     {
         throw new ExpectedException($"You can't insert manual {nameof(PointType.Gap)} points before AQTS v{MinimumGapVersion}");
     }
 }
コード例 #6
0
        private bool UpdateUser(IAquariusClient client, UserRecord userRecord, User aquariusUser)
        {
            try
            {
                var aquariusUserAuthenticationType =
                    CsvAuthenticationTypeConverter.Convert(aquariusUser.AuthenticationType);

                var user = UpdateUserByAuthenticationType[userRecord.AuthenticationType](userRecord, aquariusUser);

                if (userRecord.AuthenticationType != aquariusUserAuthenticationType)
                {
                    SwitchUserAuthenticationMode(client, userRecord, aquariusUser.UniqueId);
                }

                var updatedUser = client.Provisioning.Put(user);

                Log.Debug($"Updated {updatedUser.AuthenticationType} user: '******'");
                return(true);
            }
            catch (Exception exception)
            {
                Log.Error($"Failed to update user '{userRecord.Username}'. Error={exception.Message}");
                return(false);
            }
        }
コード例 #7
0
        private void Connect()
        {
            try
            {
                ThrowIfServerNotInstalled();
                ThrowIfWrongVersion();
                ThrowIfNotAdministrativeUser();

                _client = AquariusClient.CreateConnectedClient(_hostname, usernameTextBox.Text.Trim(),
                                                               passwordTextBox.Text);

                Info($"{Text} connected to AQTS {_client.ServerVersion} on {Environment.MachineName}");

                GetAllPlugins();

                CheckForMissingPlugins();

                connectButton.Enabled    = false;
                disconnectButton.Enabled = true;
                addButton.Enabled        = true;
            }
            catch (Exception exception)
            {
                Error(exception);
            }
        }
コード例 #8
0
        public static LocationDescription FindLocationDescription(this IAquariusClient client, string locationIdentifier)
        {
            if (client.TryGetLocationDescription(locationIdentifier, out var locationDescription))
            {
                return(locationDescription);
            }

            throw new ExpectedException($"Location '{locationIdentifier}' does not exist in the system.");
        }
コード例 #9
0
        private List <User> GetAqUsers(IAquariusClient client)
        {
            Log.Info("Retrieving existing users from Aquarius ...");
            var response = client.Provisioning.Get(new GetUsers());

            Log.Info($"Successfully retrieved {response.Results.Count} current users from Aquarius");

            return(response.Results);
        }
コード例 #10
0
ファイル: SyncStatus.cs プロジェクト: yanxuYX/examples
        public SyncStatus(IAquariusClient aquariusClient)
        {
            Client = aquariusClient;

            Settings = Client.Provisioning.Get(new GetSettings())
                       .Results
                       .ToDictionary(
                GetSettingId,
                setting => setting);
        }
コード例 #11
0
        public static Guid GetTimeSeriesUniqueId(this IAquariusClient client, string identifier)
        {
            if (Guid.TryParse(identifier, out var uniqueId))
            {
                return(uniqueId);
            }

            var timeSeriesDescription = client.GetTimeSeriesDescription(identifier);

            return(timeSeriesDescription.UniqueId);
        }
コード例 #12
0
        private TimeSeriesAppendStatus AppendPointBatch(IAquariusClient client, TimeSeries timeSeries, List <TimeSeriesPoint> points, Interval timeRange, bool isReflected, bool hasTimeRange)
        {
            AppendResponse appendResponse;

            if (isReflected)
            {
                appendResponse = client.Acquisition.Post(new PostReflectedTimeSeries
                {
                    UniqueId  = timeSeries.UniqueId,
                    TimeRange = timeRange,
                    Points    = points
                });
            }
            else
            {
                if (hasTimeRange)
                {
                    appendResponse = client.Acquisition.Post(new PostTimeSeriesOverwriteAppend
                    {
                        UniqueId  = timeSeries.UniqueId,
                        TimeRange = timeRange,
                        Points    = points
                    });
                }
                else if (points.Any() || !Notes.Any())
                {
                    appendResponse = client.Acquisition.Post(new PostTimeSeriesAppend
                    {
                        UniqueId = timeSeries.UniqueId,
                        Points   = points
                    });
                }
                else
                {
                    // We didn't have any basic points to append, but we do have notes to append.
                    // So just fake a completed status so we can move on to appending the notes.
                    return(new TimeSeriesAppendStatus
                    {
                        AppendStatus = AppendStatusCode.Completed,
                    });
                }
            }

            return(client.Acquisition.RequestAndPollUntilComplete(
                       acquisition => appendResponse,
                       (acquisition, response) => acquisition.Get(new GetTimeSeriesAppendStatus {
                AppendRequestIdentifier = response.AppendRequestIdentifier
            }),
                       polledStatus => !Context.Wait || polledStatus.AppendStatus != AppendStatusCode.Pending,
                       null,
                       Context.AppendTimeout));
        }
コード例 #13
0
ファイル: Program.cs プロジェクト: kinverarity1/examples
        private void Run()
        {
            Console.WriteLine($"Connecting to {_server} ...");

            using (_client = AquariusClient.CreateConnectedClient(_server, _username, _password))
            {
                Console.WriteLine($"Connected to {_server} ({_client.ServerVersion})");

                PollForChangedPoints();
            }

            _client = null;
        }
コード例 #14
0
        private TimeSeriesAppendStatus AppendPointBatch(IAquariusClient client, TimeSeries timeSeries, List <ReflectedTimeSeriesPoint> points, Interval timeRange, bool isReflected, bool hasTimeRange)
        {
            AppendResponse appendResponse;

            if (isReflected)
            {
                appendResponse = client.Acquisition.Post(new PostReflectedTimeSeries
                {
                    UniqueId  = timeSeries.UniqueId,
                    TimeRange = timeRange,
                    Points    = points
                });
            }
            else
            {
                var basicPoints = points
                                  .Select(p => new TimeSeriesPoint
                {
                    Time  = p.Time,
                    Value = p.Value
                })
                                  .ToList();

                if (hasTimeRange)
                {
                    appendResponse = client.Acquisition.Post(new PostTimeSeriesOverwriteAppend
                    {
                        UniqueId  = timeSeries.UniqueId,
                        TimeRange = timeRange,
                        Points    = basicPoints
                    });
                }
                else
                {
                    appendResponse = client.Acquisition.Post(new PostTimeSeriesAppend
                    {
                        UniqueId = timeSeries.UniqueId,
                        Points   = basicPoints
                    });
                }
            }

            return(client.Acquisition.RequestAndPollUntilComplete(
                       acquisition => appendResponse,
                       (acquisition, response) => acquisition.Get(new GetTimeSeriesAppendStatus {
                AppendRequestIdentifier = response.AppendRequestIdentifier
            }),
                       polledStatus => polledStatus.AppendStatus != AppendStatusCode.Pending,
                       null,
                       Context.AppendTimeout));
        }
コード例 #15
0
        public void Run()
        {
            Validate();

            using (Client = CreateConnectedClient())
            {
                LoadConfiguration();

                foreach (var processor in Processors)
                {
                    Calculate(processor);
                }
            }
        }
コード例 #16
0
        private void SwitchUserAuthenticationMode(IAquariusClient client, UserRecord userRecord, Guid uniqueId)
        {
            try
            {
                var userAuth = SwitchUserAuthenticationModeByAuthenticationType[userRecord.AuthenticationType](userRecord, uniqueId);

                var changedUser = client.Provisioning.Put(userAuth);

                Log.Debug($"Changed user '{userRecord.Username}' to authentication type {changedUser.AuthenticationType}.");
            }
            catch (Exception exception)
            {
                Log.Error($"Failed to change user '{userRecord.Username}' to authentication type {userRecord.AuthenticationType}. Error: {exception.Message}");
            }
        }
コード例 #17
0
        private void Disconnect()
        {
            if (_client != null)
            {
                Info($"Disconnected from AQTS {_client.ServerVersion} on {_hostname}");

                _client.Dispose();
                _client = null;
            }

            pluginListBox.DataSource = new BindingSource(new Dictionary<FieldDataPlugin,string>(), null);
            disconnectButton.Enabled = false;
            connectButton.Enabled = true;
            addButton.Enabled = false;
        }
コード例 #18
0
        private List <TimeSeriesPoint> LoadPointsFromNg(IAquariusClient client)
        {
            var timeSeriesInfo = client.GetTimeSeriesInfo(Context.SourceTimeSeries.Identifier);

            Log.Info($"Loading points from '{timeSeriesInfo.Identifier}' ...");

            var timeSeriesData = client.Publish.Get(new TimeSeriesDataCorrectedServiceRequest
            {
                TimeSeriesUniqueId = timeSeriesInfo.UniqueId,
                QueryFrom          = Context.SourceQueryFrom?.ToDateTimeOffset(),
                QueryTo            = Context.SourceQueryTo?.ToDateTimeOffset()
            });

            var gradesLookup     = new MetadataLookup <PublishGrade>(timeSeriesData.Grades);
            var qualifiersLookup = new MetadataLookup <PublishQualifier>(timeSeriesData.Qualifiers);

            if (!Context.IgnoreNotes)
            {
                Notes.AddRange(LoadAllNotes(client, timeSeriesInfo, timeSeriesData.Notes));
            }

            var points = timeSeriesData
                         .Points
                         .Select(p => new TimeSeriesPoint
            {
                Time       = Instant.FromDateTimeOffset(p.Timestamp.DateTimeOffset),
                Value      = p.Value.Numeric,
                GradeCode  = gradesLookup.GetFirstMetadata(p.Timestamp.DateTimeOffset, g => int.Parse(g.GradeCode)),
                Qualifiers = qualifiersLookup.GetManyMetadata(p.Timestamp.DateTimeOffset, q => q.Identifier).ToList()
            })
                         .ToList();

            var gapToleranceInMinutes = timeSeriesData.GapTolerances.Last().ToleranceInMinutes;
            var gapTolerance          = gapToleranceInMinutes.HasValue
                ? Duration.FromMinutes((long)gapToleranceInMinutes.Value)
                : DurationExtensions.MaxGapDuration;
            var interpolationType = (InterpolationType)Enum.Parse(typeof(InterpolationType), timeSeriesData.InterpolationTypes.Last().Type, true);

            SetTimeSeriesCreationProperties(
                timeSeriesInfo,
                timeSeriesData.Methods.LastOrDefault()?.MethodCode,
                gapTolerance,
                interpolationType);

            Log.Info($"Loaded {PointSummarizer.Summarize(points)} and {"note".ToQuantity(Notes.Count)} from {timeSeriesInfo.Identifier}");

            return(points);
        }
コード例 #19
0
        private static string CreateHostUrl(IAquariusClient aquariusClient)
        {
            var publishUri = (aquariusClient.Publish as JsonServiceClient)?.BaseUri;

            if (string.IsNullOrEmpty(publishUri))
            {
                return(null);
            }

            var uriBuilder = new UriBuilder(publishUri)
            {
                Path = "/AQUARIUS/AquariusDataService.svc"
            };

            return(uriBuilder.ToString());
        }
コード例 #20
0
        private IEnumerable <TimeSeriesNote> LoadAllNotes(IAquariusClient client, TimeSeries timeSeriesInfo, List <PublishNote> notes)
        {
            var corrections = client.Publish.Get(new CorrectionListServiceRequest
            {
                TimeSeriesUniqueId = timeSeriesInfo.UniqueId,
                QueryFrom          = Context.SourceQueryFrom?.ToDateTimeOffset(),
                QueryTo            = Context.SourceQueryTo?.ToDateTimeOffset()
            }).Corrections;

            var utcOffset = timeSeriesInfo.UtcOffset.ToTimeSpan();

            return(notes
                   .Select(ConvertNgNote)
                   .Concat(corrections
                           .Select(c => ConvertNgCorrection(utcOffset, c))));
        }
コード例 #21
0
        private bool CreateUser(IAquariusClient client, UserRecord userRecord)
        {
            try
            {
                var user = CreateUserByAuthenticationType[userRecord.AuthenticationType](userRecord);

                var createdUser = client.Provisioning.Post(user);

                Log.Debug($"Created {createdUser.AuthenticationType} user: '******'");
                return(true);
            }
            catch (Exception exception)
            {
                Log.Error($"Failed to create user '{userRecord.Username}'. Error={exception.Message}");
                return(false);
            }
        }
コード例 #22
0
        public static TimeSeriesDescription GetTimeSeriesDescription(this IAquariusClient client, string identifier)
        {
            var location = TimeSeriesIdentifierParser.ParseLocationIdentifier(identifier);

            var response = client.Publish.Get(new TimeSeriesDescriptionServiceRequest {
                LocationIdentifier = location
            });

            var timeSeriesDescription = response.TimeSeriesDescriptions.FirstOrDefault(t => t.Identifier == identifier);

            if (timeSeriesDescription == null)
            {
                throw new ExpectedException($"Can't find '{identifier}' at location '{location}'");
            }

            return(timeSeriesDescription);
        }
コード例 #23
0
        private int DeleteNotesWithinTimeRange(IAquariusClient client, TimeSeries timeSeries, Interval timeRange)
        {
            if (Context.IgnoreNotes)
            {
                return(0);
            }

            if (client.ServerVersion.IsLessThan(MinimumNotesVersion))
            {
                throw new ExpectedException($"You can't delete time-series notes before AQTS v{MinimumNotesVersion}");
            }

            return(client.Acquisition.Delete(new DeleteTimeSeriesNotes
            {
                UniqueId = timeSeries.UniqueId,
                TimeRange = timeRange
            }).NotesDeleted);
        }
コード例 #24
0
        private int AppendNotes(IAquariusClient client, TimeSeries timeSeries)
        {
            if (Context.IgnoreNotes || !Notes.Any())
            {
                return(0);
            }

            if (client.ServerVersion.IsLessThan(MinimumNotesVersion))
            {
                throw new ExpectedException($"You can't append time-series notes before AQTS v{MinimumNotesVersion}");
            }

            return(client.Acquisition.Post(new PostTimeSeriesMetadata
            {
                UniqueId = timeSeries.UniqueId,
                Notes = Notes
            }).NotesCreated);
        }
コード例 #25
0
        private List <ReflectedTimeSeriesPoint> LoadPointsFrom3X(IAquariusClient client)
        {
            var points = client.Publish.Get(new Get3xCorrectedData
            {
                TimeSeriesIdentifier = Context.SourceTimeSeries.Identifier,
                QueryFrom            = Context.SourceQueryFrom?.ToDateTimeOffset(),
                QueryTo = Context.SourceQueryTo?.ToDateTimeOffset()
            })
                         .Points
                         .Select(p => new ReflectedTimeSeriesPoint
            {
                Time      = Instant.FromDateTimeOffset(p.Timestamp),
                Value     = p.Value,
                GradeCode = p.Grade
            })
                         .ToList();

            Log.Info($"Loaded {points.Count} points from {Context.SourceTimeSeries.Identifier}");

            return(points);
        }
コード例 #26
0
        private void Disconnect()
        {
            if (_client != null)
            {
                Info($"Disconnected from AQTS {_client.ServerVersion} on {GetServerName()}");

                _client.Dispose();
                _client = null;
            }

            ClearPluginList();
            disconnectButton.Enabled = false;
            addButton.Enabled        = false;
            removeButton.Enabled     = false;
            priorityUpButton.Enabled = priorityDownButton.Enabled = false;
            priorityUpButton.Visible = priorityDownButton.Visible = false;
            connectButton.Enabled    = true;
            serverTextBox.Enabled    = true;
            usernameTextBox.Enabled  = true;
            passwordTextBox.Enabled  = true;
        }
コード例 #27
0
        private List <ReflectedTimeSeriesPoint> LoadPointsFromNg(IAquariusClient client)
        {
            var timeSeriesInfo = client.GetTimeSeriesInfo(Context.SourceTimeSeries.Identifier);

            Log.Info($"Loading points from '{timeSeriesInfo.Identifier}' ...");

            var timeSeriesData = client.Publish.Get(new TimeSeriesDataCorrectedServiceRequest
            {
                TimeSeriesUniqueId = timeSeriesInfo.UniqueId,
                QueryFrom          = Context.SourceQueryFrom?.ToDateTimeOffset(),
                QueryTo            = Context.SourceQueryTo?.ToDateTimeOffset()
            });

            var points = timeSeriesData
                         .Points
                         .Select(p => new ReflectedTimeSeriesPoint
            {
                Time       = Instant.FromDateTimeOffset(p.Timestamp.DateTimeOffset),
                Value      = p.Value.Numeric,
                GradeCode  = GetFirstMetadata(timeSeriesData.Grades, p.Timestamp.DateTimeOffset, g => int.Parse(g.GradeCode)),
                Qualifiers = GetManyMetadata(timeSeriesData.Qualifiers, p.Timestamp.DateTimeOffset, q => q.Identifier).ToList()
            })
                         .ToList();

            var gapToleranceInMinutes = timeSeriesData.GapTolerances.Last().ToleranceInMinutes;
            var gapTolerance          = gapToleranceInMinutes.HasValue
                ? Duration.FromMinutes((long)gapToleranceInMinutes.Value)
                : DurationExtensions.MaxGapDuration;
            var interpolationType = (InterpolationType)Enum.Parse(typeof(InterpolationType), timeSeriesData.InterpolationTypes.Last().Type, true);

            SetTimeSeriesCreationProperties(
                timeSeriesInfo,
                timeSeriesData.Methods.LastOrDefault()?.MethodCode,
                gapTolerance,
                interpolationType);

            Log.Info($"Loaded {points.Count} points from {timeSeriesInfo.Identifier}");

            return(points);
        }
コード例 #28
0
        public static bool TryGetLocationDescription(this IAquariusClient client, string locationIdentifier, out LocationDescription locationDescription)
        {
            var locationDescriptions = client.Publish.Get(new LocationDescriptionListServiceRequest
            {
                LocationIdentifier = locationIdentifier
            }).LocationDescriptions;

            if (locationDescriptions.Count == 1)
            {
                locationDescription = locationDescriptions
                                      .First();

                return(true);
            }

            locationDescription = default;

            if (!locationDescriptions.Any())
            {
                return(false);
            }

            throw new ExpectedException($"{locationDescriptions.Count} ambiguous location identifiers matched '{locationIdentifier}': {string.Join(", ", locationDescriptions.Select(l => l.Identifier))}");
        }
コード例 #29
0
ファイル: ReportRunner.cs プロジェクト: yanxuYX/examples
 public ReportRunner(Context context)
 {
     _context = context;
     _client  = CreateConnectedClient();
 }
コード例 #30
0
        private List <TimeSeriesPoint> LoadPointsFrom3X(IAquariusClient client)
        {
            var timeSeriesDescription = client.Publish.Get(new Get3xTimeSeriesDescription
            {
                LocationIdentifier = Context.SourceTimeSeries.LocationIdentifier,
                Parameter          = Context.SourceTimeSeries.Parameter
            })
                                        .TimeSeriesDescriptions
                                        .SingleOrDefault(ts => ts.Identifier == Context.SourceTimeSeries.TargetIdentifier);

            if (timeSeriesDescription == null)
            {
                throw new ExpectedException($"Can't find '{Context.SourceTimeSeries.Identifier}' time-series in location '{Context.SourceTimeSeries.LocationIdentifier}'.");
            }

            Log.Info($"Loading points from '{timeSeriesDescription.Identifier}' ...");

            var correctedData = client.Publish.Get(new Get3xCorrectedData
            {
                TimeSeriesIdentifier = Context.SourceTimeSeries.Identifier,
                QueryFrom            = Context.SourceQueryFrom?.ToDateTimeOffset(),
                QueryTo = Context.SourceQueryTo?.ToDateTimeOffset()
            });

            var points = correctedData
                         .Points
                         .Select(p => new TimeSeriesPoint
            {
                Time      = Instant.FromDateTimeOffset(p.Timestamp),
                Value     = p.Value,
                GradeCode = p.Grade
            })
                         .ToList();

            // 3.X Publish API's TimeSeriesDescription is missing some info, so grab those pieces from elsewhere

            // The time-range start will always be in the offset of the time-series, even when no points exist
            var utcOffset = Offset.FromHoursAndMinutes(correctedData.TimeRange.StartTime.Offset.Hours, correctedData.TimeRange.StartTime.Offset.Minutes);

            // We can infer the interpolationType from the last point (if one exists)
            var interpolationType = Context.InterpolationType ?? (correctedData.Points.Any()
                                        ? (InterpolationType?)correctedData.Points.Last().Interpolation
                                        : null);

            var timeSeries = new TimeSeries
            {
                Identifier                  = Context.SourceTimeSeries.Identifier,
                Parameter                   = timeSeriesDescription.Parameter,
                Label                       = timeSeriesDescription.Label,
                Unit                        = timeSeriesDescription.Unit,
                Publish                     = timeSeriesDescription.Publish,
                Description                 = timeSeriesDescription.Description,
                Comment                     = timeSeriesDescription.Comment,
                TimeSeriesType              = KnownTimeSeriesTypes[timeSeriesDescription.TimeSeriesType],
                UtcOffset                   = utcOffset,
                ComputationIdentifier       = timeSeriesDescription.ComputationIdentifier,
                ComputationPeriodIdentifier = timeSeriesDescription.ComputationPeriodIdentifier,
                SubLocationIdentifier       = timeSeriesDescription.SubLocationIdentifier,
                LocationIdentifier          = timeSeriesDescription.LocationIdentifier,
                ExtendedAttributeValues     = timeSeriesDescription.ExtendedAttributes.Select(ea =>
                                                                                              new ExtendedAttributeValue
                {
                    ColumnIdentifier = $"{ea.Name.ToUpperInvariant()}@TIMESERIES_EXTENSION",
                    Value            = ea.Value?.ToString()
                })
                                              .ToList()
            };

            SetTimeSeriesCreationProperties(timeSeries, interpolationType: interpolationType);

            if (!Context.IgnoreNotes)
            {
                var corrections = client.Publish.Get(new Get3xCorrectionList
                {
                    TimeSeriesIdentifier = Context.SourceTimeSeries.Identifier,
                    QueryFrom            = Context.SourceQueryFrom?.ToDateTimeOffset(),
                    QueryTo = Context.SourceQueryTo?.ToDateTimeOffset()
                }).Corrections;

                var utcTimespan = utcOffset.ToTimeSpan();
                Notes.AddRange(corrections.Select(c => Convert3XCorrection(utcTimespan, c)));
            }

            Log.Info($"Loaded {PointSummarizer.Summarize(points)} and {"note".ToQuantity(Notes.Count)} from {Context.SourceTimeSeries.Identifier}");

            return(points);
        }