Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
69 commits
Select commit Hold shift + click to select a range
12dee66
Fix issue with AssetType filters
prestoncraw Jul 31, 2026
fda8048
move filter logic to getEnum
prestoncraw Jul 31, 2026
bd83463
update pointer
prestoncraw Jul 31, 2026
07dbb2c
Filter out Assets that are of type LineSegment
prestoncraw Jul 31, 2026
7e8bc3d
Merge pull request #136 from GridProtectionAlliance/PQB-114
prestoncraw Aug 3, 2026
461bdec
Initial implementation of statistics widget
prestoncraw Aug 3, 2026
98e60d2
Remove settings that Histogram Widget doesnt support
prestoncraw Aug 3, 2026
2455265
Fix broken marker overlays
prestoncraw Aug 3, 2026
cd6651d
Add support for markers on histogram widget
prestoncraw Aug 3, 2026
050f07b
Add GroupBy ChannelGroup options for Histogram/Statistics widgets
prestoncraw Aug 3, 2026
e1ce9a8
Merge pull request #137 from GridProtectionAlliance/PQB-113-StatsTable
clackner-gpa Aug 5, 2026
8060f1d
Fix generic type usage in NotesController for record addition
prestoncraw Aug 6, 2026
c89ecca
update pointer
prestoncraw Aug 6, 2026
5d6d1cc
update submodule pointer
prestoncraw Aug 6, 2026
127ec79
address comments/simplify
prestoncraw Aug 6, 2026
e3bbafa
Merge pull request #141 from GridProtectionAlliance/NoteControllerFix
prestoncraw Aug 6, 2026
25dde0a
Migrate libraries to PQDigest
prestoncraw Aug 3, 2026
9359e7c
Remove remaining libaries that live in PQDigest
prestoncraw Aug 3, 2026
15fd061
add missing proj reference
prestoncraw Aug 4, 2026
ba44849
update pointer
prestoncraw Aug 10, 2026
60ed2ac
Merge pull request #138 from GridProtectionAlliance/Library_Migration
clackner-gpa Aug 10, 2026
a24e8dc
Fix time handling for trend plots (PQB-117)
prestoncraw Aug 7, 2026
c5f1474
Merge pull request #142 from GridProtectionAlliance/Trend_TimeZones
clackner-gpa Aug 12, 2026
d99a0e0
add tsx-conventions
prestoncraw Aug 7, 2026
6a04ece
Cleanup
prestoncraw Aug 7, 2026
1157665
Add ability to export trending widget data from individual widgets
prestoncraw Aug 10, 2026
ca154cc
update gemstone
prestoncraw Aug 13, 2026
92bf6eb
Fix label
prestoncraw Aug 13, 2026
d722d4d
Merge pull request #145 from GridProtectionAlliance/Trend_CSVExport
clackner-gpa Aug 13, 2026
e661866
Add systemname to sidebar
prestoncraw Aug 13, 2026
6bd26f2
Fix issue with awkward table rendering
prestoncraw Aug 13, 2026
94f06f1
Change event characterisits setter to be evt based instead of effect …
prestoncraw Aug 13, 2026
43c04d2
Merge pull request #147 from GridProtectionAlliance/SystemName
clackner-gpa Aug 13, 2026
e219ebb
Update gemstone and fix vulns
prestoncraw Aug 14, 2026
8a89c8e
Change icon for results message
prestoncraw Aug 14, 2026
7b31e41
Merge pull request #148 from GridProtectionAlliance/GemstoneUpdate
clackner-gpa Aug 14, 2026
1341fb5
Added Packages for Map
clackner-gpa Aug 14, 2026
0edee86
Removed timeout od settings call
clackner-gpa Aug 14, 2026
3df8b44
Avoid call to get Widgets without Category
clackner-gpa Aug 14, 2026
5aa05c2
Added ESRI Authetication
clackner-gpa Aug 14, 2026
b2ea50d
Updated EventWidgets
clackner-gpa Aug 14, 2026
d01d16a
update pointer
prestoncraw Aug 17, 2026
4e4e526
update pointer
prestoncraw Aug 17, 2026
4b2b283
fix vulns
prestoncraw Aug 17, 2026
d9df6d9
Merge pull request #149 from GridProtectionAlliance/PQP-124
prestoncraw Aug 17, 2026
7681586
Remove legacy build files
prestoncraw Aug 4, 2026
fb29837
Add Publish Profiles
prestoncraw Aug 4, 2026
03494aa
add dockerfile
prestoncraw Aug 4, 2026
c0780ac
Add logic to disable auth
prestoncraw Aug 4, 2026
6ed9ead
add jenkinsfile and update sln/proj files
prestoncraw Aug 4, 2026
42224b3
Rename SEBrowser.version to PQBrowser.version
clackner-gpa Aug 10, 2026
94ac172
Address comments
prestoncraw Aug 10, 2026
6e98173
rename folders,files, and namespaces referencing SEBrowser intead of …
prestoncraw Aug 10, 2026
61473c6
remove version name from the UI build and move to a query param
prestoncraw Aug 12, 2026
89ca22b
remove unnecessarychecks
prestoncraw Aug 12, 2026
c2aa4e2
remove uneccessary env var
prestoncraw Aug 13, 2026
a0fb398
Fix WebPublishMethod
prestoncraw Aug 13, 2026
735e088
Address comments
prestoncraw Aug 13, 2026
f0d9286
add lint to jenkinsfile
prestoncraw Aug 14, 2026
cefa2e3
Add submodule pointer update logic
prestoncraw Aug 14, 2026
815db1f
update steps
prestoncraw Aug 14, 2026
902523c
update pointer
prestoncraw Aug 17, 2026
7d93960
Merge pull request #139 from GridProtectionAlliance/JenkinsDocker_Sup…
clackner-gpa Aug 17, 2026
0fd9dc1
Updated Dependencies
gsfbuildbot Aug 17, 2026
068642e
Updated Dependencies
gsfbuildbot Aug 18, 2026
5df348d
Utilize correct dep
prestoncraw Aug 18, 2026
26e8d11
fix incorrect ref
prestoncraw Aug 18, 2026
d4ee8f9
utilize dotnet instead of msbuild for publishing
prestoncraw Aug 18, 2026
bbf621c
fix issue with constants
prestoncraw Aug 18, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
18 changes: 11 additions & 7 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,8 @@ bld/
[Oo]bj/
[Cc]onfiguration[Cc]ache/
Publish
SEBrowser/DynamicAssemblies/
SEBrowser/Scripts/SEBrowser.js
PQBrowser/DynamicAssemblies/
PQBrowser/Scripts/PQBrowser.js

# Visual Studio 2015 cache/options directory
.vs/
Expand Down Expand Up @@ -144,6 +144,10 @@ publish/
# TODO: Comment the next line if you want to checkin your web deploy settings
# but database connection strings (with potential passwords) will be unencrypted
*.pubxml
!PQBrowser/Properties/PublishProfiles/Development Profile PQBrowser.pubxml
!PQBrowser/Properties/PublishProfiles/Release Profile PQBrowser.pubxml
!PQBrowser/Properties/PublishProfiles/Docker Development Profile PQBrowser.pubxml
!PQBrowser/Properties/PublishProfiles/Docker Release Profile PQBrowser.pubxml
*.publishproj

# NuGet Packages
Expand Down Expand Up @@ -224,9 +228,9 @@ _Pvt_Extensions

# Ignore files generated by web app in debug mode
/Publish.zip
/SEBrowser/NUglify.dll
/PQBrowser/NUglify.dll
/Dependencies/NuGet
/SEBrowser/web.config.backup
/SEBrowser/Scripts/vendors-node_modules_canvg_lib_index_es_js.js
/SEBrowser/Scripts/vendors-node_modules_dompurify_dist_purify_js.js
/SEBrowser/Web.config
/PQBrowser/web.config.backup
/PQBrowser/Scripts/vendors-node_modules_canvg_lib_index_es_js.js
/PQBrowser/Scripts/vendors-node_modules_dompurify_dist_purify_js.js
/PQBrowser/Web.config
4 changes: 2 additions & 2 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
[submodule "SEBrowser/EventWidgets"]
path = SEBrowser/EventWidgets
[submodule "PQBrowser/EventWidgets"]
path = PQBrowser/EventWidgets
url = https://github.com/GridProtectionAlliance/EventWidgets.git
3 changes: 3 additions & 0 deletions AGENTS.MD
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
## React/TSX conventions

Before creating, editing, refactoring, or reviewing any `.tsx` file, read and follow `docs/conventions/tsx-conventions.md`.
1 change: 1 addition & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
@AGENTS.md
Binary file added Dependencies/OpenXDA/FaultAlgorithms.dll
Binary file not shown.
Binary file added Dependencies/OpenXDA/FaultData.dll
Binary file not shown.
Binary file added Dependencies/OpenXDA/openHistorian.XDALink.dll
Binary file not shown.
Binary file not shown.
Binary file added Dependencies/OpenXDA/openXDA.Configuration.dll
Binary file not shown.
Binary file added Dependencies/OpenXDA/openXDA.Model.dll
Binary file not shown.
Binary file added Dependencies/OpenXDA/openXDA.PQI.dll
Binary file not shown.
Binary file added Dependencies/OpenXDA/openXDA.Reports.dll
Binary file not shown.
4 changes: 2 additions & 2 deletions Directory.Build.props
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<Project>
<Project>
<PropertyGroup>
<GemstoneVersion>1.0.179</GemstoneVersion>
<GemstoneVersion>1.0.181</GemstoneVersion>
</PropertyGroup>
</Project>
326 changes: 326 additions & 0 deletions Jenkinsfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,326 @@
import hudson.model.Result
import jenkins.model.CauseOfInterruption
import org.jenkinsci.plugins.workflow.steps.FlowInterruptedException

def haltBuildWithSuccess() {
currentBuild.rawBuild.@result = Result.SUCCESS
def cause = new CauseOfInterruption.UserInterruption("Build halted programmatically with SUCCESS status")
throw new FlowInterruptedException(Result.SUCCESS, false, cause)
}

pipeline {
agent any

environment {
github_pat = credentials('github-pat')
devBranch = "development"
mainBranch = "master"
NUGET_PACKAGES = "D:\\NuGetCache"
}

stages {
stage('Prepare Environment') {
steps {
script {
// Set current Version
def fileContent = powershell(returnStdout: true, script: '''
Get-Content -Path "./Scripts/PQBrowser.version" -Raw
''').trim()
env.pqBrowserVersion = fileContent
println("PQBrowser version: ${env.pqBrowserVersion}")
}
script {
//Set current Commit
env.GIT_COMMIT = bat(script: '@git rev-parse HEAD', returnStdout: true).trim()
println("Current Git Commit: ${env.GIT_COMMIT}")
}
script {
//Get last release from git tags
bat( script: "@git fetch origin ${env.mainBranch}:refs/remotes/origin/${env.mainBranch}")
def mainCommit = bat(script: "@git rev-parse origin/${env.mainBranch}", returnStdout: true).trim()

try {
env.LAST_RELEASE_TAG = bat(script: "@git describe --tags --abbrev=0 ${mainCommit}", returnStdout: true).trim()
}
catch (Exception ex) {
println("No tags found, setting LAST_RELEASE_TAG to v3.0.0")
env.LAST_RELEASE_TAG = "v3.0.0"
}
println("Last Release Tag: ${env.LAST_RELEASE_TAG}")
}
}
}

stage('Check Conditions') {
when {
anyOf {
not {
anyOf {
expression { env.BRANCH_NAME.startsWith("PR") }
expression { env.BRANCH_NAME == "${env.mainBranch}" }
}
}
allOf {
expression { env.BRANCH_NAME.startsWith("PR") }
expression { env.CHANGE_BRANCH != "${env.devBranch}" }
}
allOf {
expression { env.BRANCH_NAME.startsWith("PR") }
expression { env.CHANGE_TARGET != "${env.mainBranch}" }
}
}
}
steps {
haltBuildWithSuccess()
}
}

stage('Checkout Master Branch') {
when {
expression {
return env.BRANCH_NAME == "${env.mainBranch}"
}
}
steps {
script {
bat(script: "@git fetch origin ${env.BRANCH_NAME}:refs/remotes/origin/${env.BRANCH_NAME}")
bat(script: "@git checkout origin/${env.BRANCH_NAME}")
}
}
}

stage('Checkout Development Branch') {
when {
expression {
return env.CHANGE_BRANCH == "${env.devBranch}"
}
}
steps {
script {
bat(script: "@git fetch origin ${env.CHANGE_BRANCH}:refs/remotes/origin/${env.CHANGE_BRANCH}")
bat(script: "@git checkout origin/${env.CHANGE_BRANCH}")
}
}
}

stage('Checkout Submodules') {
steps {
bat(script: '@git submodule sync --recursive')
bat(script: '@git submodule update --init --recursive')
bat(script: '@git submodule status --recursive')
}
}

stage('Application Version') {
when {
expression {
return env.BRANCH_NAME != "${env.mainBranch}"
}
}
steps {
script {
env.GIT_COMMIT = bat(script: '@git rev-parse HEAD', returnStdout: true).trim()
}
powershell "powershell.exe -File .\\Scripts\\Versioning.ps1 -VersionFile './Scripts/PQBrowser.version' -Commit false"
bat(script: "@git add Scripts/PQBrowser.version")
bat(script: "git diff --cached --quiet || git commit -m \"Updated Version Number\"")
}
}

stage('Gemstone Updates') {
when {
expression {
return env.BRANCH_NAME != "${env.mainBranch}"
}
}
steps {
powershell "powershell.exe -File .\\Scripts\\GemstoneUpdates.ps1 -VersionFile './Directory.Build.props'"
powershell "powershell.exe -File .\\Scripts\\CreateDependencyPR.ps1 -GithubToken '${github_pat}' -DevelopmentBranchName '${devBranch}'"
script {
bat(script: "@git add Directory.Build.props")
// Avoid an empty commit, which would return a failure code when the pointer is current.
bat(script: "git diff --cached --quiet || git commit -m \"Updated Dependencies\"")
}
}
}

stage('EventWidgets Pointer Update') {
when {
expression {
return env.BRANCH_NAME != "${env.mainBranch}"
}
}
steps {
dir('PQBrowser/EventWidgets') {
bat(script: '@git fetch origin main')
bat(script: '@git checkout origin/main')
}
script {
bat(script: '@git add PQBrowser/EventWidgets')
// Avoid an empty commit, which would return a failure code when the pointer is current.
bat(script: 'git diff --cached --quiet || git commit -m "Updated EventWidgets Pointer"')
}
}
}

stage('Push Changes') {
when {
allOf {
expression {
return env.BRANCH_NAME != "${env.mainBranch}"
}
expression {
return bat(script: '@git rev-parse HEAD', returnStdout: true).trim() != env.GIT_COMMIT
}
}
}
steps {
powershell "git push origin HEAD:${env.devBranch}"
haltBuildWithSuccess()
}
}

stage('Install UI Dependencies') {
steps {
dir('PQBrowser') {
bat(script: 'npm ci')
}
}
}

stage('Lint') {
when {
allOf {
expression {
return env.CHANGE_BRANCH == "${env.devBranch}"
}
expression {
return env.CHANGE_TARGET == "${env.mainBranch}"
}
}
}
steps {
dir('PQBrowser') {
bat(script: 'npm run lint')
}
}
}

stage('Build Production UI') {
steps {
dir('PQBrowser') {
bat(script: 'npm run build')
}
}
}

stage('Build Docker Images') {
when {
anyOf {
expression {
return env.CHANGE_BRANCH == "${env.devBranch}"
}
expression {
return env.BRANCH_NAME == "${env.mainBranch}"
}
}
}
steps {
script {
env.pqBrowserDockerTag = env.CHANGE_BRANCH == "${env.devBranch}" ? "${env.pqBrowserVersion}a" : env.pqBrowserVersion
println("Building PQBrowser Docker image tag: pqbrowser:${env.pqBrowserDockerTag}")
}

powershell """
dotnet publish '.\\PQBrowser\\PQBrowser.csproj' `
--configuration Release `
'-p:PublishProfile=Docker Release Profile PQBrowser'
"""

powershell "docker build --build-arg CONFIGURATION=Release -f .\\PQBrowser.dockerfile -t pqbrowser:${env.pqBrowserDockerTag} ."
}
}

stage('Publish Application') {
steps {
powershell """
dotnet publish '.\\PQBrowser\\PQBrowser.csproj' `
'-p:PublishProfile=Release Profile PQBrowser'
"""
}
}

stage('Package Application') {
steps {
script {
if (!env.WEBHOST_DELIVERY_DIRECTORY?.trim()) {
error('WEBHOST_DELIVERY_DIRECTORY is not configured in Jenkins.')
}

env.archiveName = env.BRANCH_NAME == "${env.mainBranch}" ?
"PQBrowser_v${env.pqBrowserVersion}.zip" :
"PQBrowser_v${env.pqBrowserVersion}a.zip"
}
powershell """
[xml]\$publishProfile = Get-Content `
-LiteralPath '.\\PQBrowser\\Properties\\PublishProfiles\\Release Profile PQBrowser.pubxml' `
-Raw
\$publishDir = (\$publishProfile.Project.PropertyGroup |
Where-Object { \$_.PublishDir }).PublishDir

Compress-Archive `
-Path (Join-Path '.\\PQBrowser' "\$publishDir*") `
-DestinationPath '${WORKSPACE}\\${env.archiveName}' `
-Force
"""
}
}

stage('Comment Prerelease') {
when {
expression {
return env.CHANGE_BRANCH == "${env.devBranch}"
}
}
steps {
powershell """
powershell.exe -File .\\Scripts\\GithubComment.ps1 `
-Comment 'Prerelease PQBrowser v${env.pqBrowserVersion}a is available.' `
-BranchName '${env.devBranch}' `
-GithubToken '${github_pat}' `
-RepoOwner 'GridProtectionAlliance' `
-RepoName 'SEBrowser'
"""
}
}

stage('Deploy Prerelease') {
when {
expression {
return env.CHANGE_BRANCH == "${env.devBranch}"
}
}
steps {
powershell "Move-Item -Path '${WORKSPACE}\\${env.archiveName}' -Destination '${env.WEBHOST_DELIVERY_DIRECTORY}\\PQBrowser\\PreRelease\\${env.archiveName}' -Force"
}
}

stage('Deploy Release') {
when {
allOf {
expression {
return env.BRANCH_NAME == "${env.mainBranch}"
}
expression {
return "v${env.pqBrowserVersion}" != env.LAST_RELEASE_TAG
}
}
}
steps {
powershell "Move-Item -Path '${WORKSPACE}\\${env.archiveName}' -Destination '${env.WEBHOST_DELIVERY_DIRECTORY}\\PQBrowser\\${env.archiveName}' -Force"
powershell "git tag -a v${env.pqBrowserVersion} -m 'Version ${env.pqBrowserVersion} release'"
powershell "git push origin --tags"
}
}
}
}
Loading