@@ -3403,7 +3403,7 @@ const SettingsForms = {
3403
3403
const appType = container . getAttribute ( 'data-app-type' ) || 'general' ;
3404
3404
3405
3405
// Skip auto-save for all forms - they now use manual save
3406
- const manualSaveApps = [ 'swaparr' , 'general' , 'notifications' , 'sonarr' , 'radarr' , 'lidarr' , 'readarr' , 'whisparr' , 'eros' ] ;
3406
+ const manualSaveApps = [ 'swaparr' , 'general' , 'notifications' , 'sonarr' , 'radarr' , 'lidarr' , 'readarr' , 'whisparr' , 'eros' , 'prowlarr' ] ;
3407
3407
if ( manualSaveApps . includes ( appType ) ) {
3408
3408
console . log ( `[SettingsForms] Skipping auto-save setup for ${ appType } - using manual save` ) ;
3409
3409
return ;
@@ -4111,6 +4111,15 @@ const SettingsForms = {
4111
4111
settings . quality_based_removal = getInputValue ( '#swaparr_quality_based_removal' , false ) ;
4112
4112
settings . blocked_quality_patterns = this . getTagsFromContainer ( 'swaparr_quality_patterns_tags' ) ;
4113
4113
}
4114
+ else if ( appType === 'prowlarr' ) {
4115
+ // Prowlarr doesn't use instances array, store directly
4116
+ settings . instances = [ ] ;
4117
+
4118
+ settings . enabled = getInputValue ( '#prowlarr-enabled-0' , true ) ;
4119
+ settings . name = getInputValue ( '#prowlarr-name-0' , 'Prowlarr' ) ;
4120
+ settings . api_url = getInputValue ( '#prowlarr-url-0' , '' ) ;
4121
+ settings . api_key = getInputValue ( '#prowlarr-key-0' , '' ) ;
4122
+ }
4114
4123
}
4115
4124
4116
4125
console . log ( 'Collected settings for' , appType , settings ) ;
@@ -5142,7 +5151,7 @@ const SettingsForms = {
5142
5151
5143
5152
// Check connection status for an instance
5144
5153
checkConnectionStatus : function ( app , instanceIndex ) {
5145
- const supportedApps = [ 'radarr' , 'sonarr' , 'lidarr' , 'readarr' , 'whisparr' , 'eros' ] ;
5154
+ const supportedApps = [ 'radarr' , 'sonarr' , 'lidarr' , 'readarr' , 'whisparr' , 'eros' , 'prowlarr' ] ;
5146
5155
if ( ! supportedApps . includes ( app ) ) return ;
5147
5156
5148
5157
const urlInput = document . getElementById ( `${ app } -url-${ instanceIndex } ` ) ;
@@ -5640,7 +5649,7 @@ const SettingsForms = {
5640
5649
// Only remove if all sections have no unsaved changes
5641
5650
if ( ! window . swaparrUnsavedChanges && ! window . settingsUnsavedChanges && ! window . notificationsUnsavedChanges &&
5642
5651
! window . sonarrUnsavedChanges && ! window . radarrUnsavedChanges && ! window . lidarrUnsavedChanges &&
5643
- ! window . readarrUnsavedChanges && ! window . whisparrUnsavedChanges && ! window . erosUnsavedChanges ) {
5652
+ ! window . readarrUnsavedChanges && ! window . whisparrUnsavedChanges && ! window . erosUnsavedChanges && ! window . prowlarrUnsavedChanges ) {
5644
5653
// Remove beforeunload event listener
5645
5654
if ( window . huntarrBeforeUnloadListener ) {
5646
5655
window . removeEventListener ( 'beforeunload' , window . huntarrBeforeUnloadListener ) ;
@@ -5712,7 +5721,7 @@ const SettingsForms = {
5712
5721
}
5713
5722
5714
5723
// Check each app instance for unsaved changes
5715
- const appTypes = [ 'sonarr' , 'radarr' , 'lidarr' , 'readarr' , 'whisparr' , 'eros' ] ;
5724
+ const appTypes = [ 'sonarr' , 'radarr' , 'lidarr' , 'readarr' , 'whisparr' , 'eros' , 'prowlarr' ] ;
5716
5725
for ( const appType of appTypes ) {
5717
5726
const unsavedChangesVar = `${ appType } UnsavedChanges` ;
5718
5727
if ( window [ unsavedChangesVar ] ) {
@@ -5738,6 +5747,136 @@ const SettingsForms = {
5738
5747
}
5739
5748
5740
5749
return true ; // No unsaved changes, can proceed
5750
+ } ,
5751
+
5752
+ // Generate Prowlarr settings form
5753
+ generateProwlarrForm : function ( container , settings = { } ) {
5754
+ // Ensure settings is a valid object
5755
+ if ( ! settings || typeof settings !== 'object' ) {
5756
+ settings = { } ;
5757
+ }
5758
+
5759
+ // Add data-app-type attribute to container
5760
+ container . setAttribute ( 'data-app-type' , 'prowlarr' ) ;
5761
+
5762
+ // Add save button at the top
5763
+ let prowlarrSaveButtonHtml = `
5764
+ <div style="margin-bottom: 20px;">
5765
+ <button type="button" id="prowlarr-save-button" disabled style="
5766
+ background: #6b7280;
5767
+ color: #9ca3af;
5768
+ border: 1px solid #4b5563;
5769
+ padding: 8px 16px;
5770
+ border-radius: 6px;
5771
+ font-size: 14px;
5772
+ font-weight: 500;
5773
+ cursor: not-allowed;
5774
+ display: flex;
5775
+ align-items: center;
5776
+ gap: 8px;
5777
+ transition: all 0.2s ease;
5778
+ ">
5779
+ <i class="fas fa-save"></i>
5780
+ Save Changes
5781
+ </button>
5782
+ </div>
5783
+ ` ;
5784
+
5785
+ // Create the Prowlarr configuration container
5786
+ let prowlarrHtml = `
5787
+ <div class="settings-group" style="
5788
+ background: linear-gradient(135deg, #0f172a 0%, #1e293b 50%, #334155 100%);
5789
+ border: 2px solid rgba(90, 109, 137, 0.3);
5790
+ border-radius: 12px;
5791
+ padding: 20px;
5792
+ margin: 15px 0 25px 0;
5793
+ box-shadow: 0 4px 12px rgba(90, 109, 137, 0.1), inset 0 1px 0 rgba(255, 255, 255, 0.1);
5794
+ ">
5795
+ <h3>Prowlarr Configuration</h3>
5796
+ <div class="prowlarr-container">
5797
+ <div class="prowlarr-item" data-instance-id="0">
5798
+ <div class="prowlarr-header">
5799
+ <h4>Prowlarr</h4>
5800
+ <div class="prowlarr-actions">
5801
+ <span class="connection-status" id="prowlarr-status-0" style="margin-left: 10px; font-weight: bold; font-size: 0.9em;"></span>
5802
+ </div>
5803
+ </div>
5804
+ <div class="prowlarr-content">
5805
+ <div class="setting-item">
5806
+ <label for="prowlarr-enabled-0">Enabled:</label>
5807
+ <label class="toggle-switch" style="width:40px; height:20px; display:inline-block; position:relative;">
5808
+ <input type="checkbox" id="prowlarr-enabled-0" name="enabled" ${ settings . enabled !== false ? 'checked' : '' } >
5809
+ <span class="toggle-slider" style="position:absolute; cursor:pointer; top:0; left:0; right:0; bottom:0; background-color:#3d4353; border-radius:20px; transition:0.4s;"></span>
5810
+ </label>
5811
+ <p class="setting-help">Enable or disable Prowlarr integration</p>
5812
+ </div>
5813
+ <div class="setting-item">
5814
+ <label for="prowlarr-name-0">Name:</label>
5815
+ <input type="text" id="prowlarr-name-0" name="name" value="${ settings . name || 'Prowlarr' } " placeholder="Friendly name for Prowlarr">
5816
+ <p class="setting-help">Friendly name for this Prowlarr instance</p>
5817
+ </div>
5818
+ <div class="setting-item">
5819
+ <label for="prowlarr-url-0">URL:</label>
5820
+ <input type="text" id="prowlarr-url-0" name="api_url" value="${ settings . api_url || '' } " placeholder="Base URL for Prowlarr (e.g., http://localhost:9696)" data-instance-index="0">
5821
+ <p class="setting-help">Base URL for Prowlarr (e.g., http://localhost:9696)</p>
5822
+ </div>
5823
+ <div class="setting-item">
5824
+ <label for="prowlarr-key-0">API Key:</label>
5825
+ <input type="text" id="prowlarr-key-0" name="api_key" value="${ settings . api_key || '' } " placeholder="API key for Prowlarr" data-instance-index="0">
5826
+ <p class="setting-help">API key for Prowlarr</p>
5827
+ </div>
5828
+ </div>
5829
+ </div>
5830
+ </div>
5831
+ </div>
5832
+ ` ;
5833
+
5834
+ // Set the content with save button at the top
5835
+ container . innerHTML = prowlarrSaveButtonHtml + prowlarrHtml ;
5836
+
5837
+ // Setup auto-detection (like Sonarr)
5838
+ this . setupProwlarrAutoDetection ( container ) ;
5839
+
5840
+ // Set up manual save functionality for Prowlarr
5841
+ this . setupAppManualSave ( container , 'prowlarr' , settings ) ;
5842
+ } ,
5843
+
5844
+ // Setup auto-detection for Prowlarr (similar to Sonarr)
5845
+ setupProwlarrAutoDetection : function ( container ) {
5846
+ console . log ( '[SettingsForms] Setting up Prowlarr auto-detection' ) ;
5847
+
5848
+ // Find URL and API key inputs
5849
+ const urlInput = container . querySelector ( '#prowlarr-url-0' ) ;
5850
+ const apiKeyInput = container . querySelector ( '#prowlarr-key-0' ) ;
5851
+
5852
+ if ( urlInput ) {
5853
+ urlInput . addEventListener ( 'input' , ( ) => {
5854
+ setTimeout ( ( ) => {
5855
+ this . checkConnectionStatus ( 'prowlarr' , 0 ) ;
5856
+ } , 1000 ) ; // 1 second delay to prevent spam while typing
5857
+ } ) ;
5858
+ urlInput . addEventListener ( 'blur' , ( ) => {
5859
+ this . checkConnectionStatus ( 'prowlarr' , 0 ) ;
5860
+ } ) ;
5861
+ }
5862
+
5863
+ if ( apiKeyInput ) {
5864
+ apiKeyInput . addEventListener ( 'input' , ( ) => {
5865
+ setTimeout ( ( ) => {
5866
+ this . checkConnectionStatus ( 'prowlarr' , 0 ) ;
5867
+ } , 1000 ) ; // 1 second delay to prevent spam while typing
5868
+ } ) ;
5869
+ apiKeyInput . addEventListener ( 'blur' , ( ) => {
5870
+ this . checkConnectionStatus ( 'prowlarr' , 0 ) ;
5871
+ } ) ;
5872
+ }
5873
+
5874
+ // Initial status check if URL and key are provided
5875
+ if ( urlInput && apiKeyInput && urlInput . value . trim ( ) && apiKeyInput . value . trim ( ) ) {
5876
+ setTimeout ( ( ) => {
5877
+ this . checkConnectionStatus ( 'prowlarr' , 0 ) ;
5878
+ } , 500 ) ;
5879
+ }
5741
5880
}
5742
5881
} ;
5743
5882
0 commit comments