Compare commits
354 Commits
0.7.0Beta4
...
0.7.9
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
c237ddfef4 | ||
|
|
b543dcb5ac | ||
|
|
ccfbb07333 | ||
|
|
256ccbd6a1 | ||
|
|
d8d507f110 | ||
|
|
7b3309649f | ||
|
|
9a7a6652e8 | ||
|
|
db4891748f | ||
|
|
3dce2e8908 | ||
|
|
c91291c315 | ||
|
|
a2a5a1f8e4 | ||
|
|
7651f709ad | ||
|
|
a565077348 | ||
|
|
6cf99e7d3a | ||
|
|
f730a82005 | ||
|
|
5449607c1d | ||
|
|
c62415abfd | ||
|
|
dcbea3057c | ||
|
|
91642d16c8 | ||
|
|
2f2773149d | ||
|
|
adaba03f50 | ||
|
|
58a5e09540 | ||
|
|
20dc906095 | ||
|
|
e2f41d3761 | ||
|
|
ab1372c7fc | ||
|
|
e305678cf4 | ||
|
|
a82df9bf2e | ||
|
|
986604f27c | ||
|
|
59324c7453 | ||
|
|
91613a5b37 | ||
|
|
5ca05fd2c0 | ||
|
|
4d4045cff4 | ||
|
|
1f209a42d8 | ||
|
|
bffbb362db | ||
|
|
435eed8818 | ||
|
|
f86656543a | ||
|
|
9c510c6dd1 | ||
|
|
f81ab3d1c0 | ||
|
|
d1585c28a9 | ||
|
|
9c314532c0 | ||
|
|
853bda5d86 | ||
|
|
d05e31f7f0 | ||
|
|
383354871d | ||
|
|
2086a217e0 | ||
|
|
34f3574746 | ||
|
|
1dfe0b957e | ||
|
|
17d14bc3b4 | ||
|
|
885032e436 | ||
|
|
ceee95aaf7 | ||
|
|
bc6b3091eb | ||
|
|
4be1a13316 | ||
|
|
a77327ee7f | ||
|
|
aa706012af | ||
|
|
f5b6203194 | ||
|
|
1ced9a54e4 | ||
|
|
06c7089a77 | ||
|
|
ee1d864eea | ||
|
|
d703338935 | ||
|
|
e87b24c460 | ||
|
|
3404ef6516 | ||
|
|
181897e92b | ||
|
|
26a504e3e2 | ||
|
|
b72ed09011 | ||
|
|
bb99c0d58e | ||
|
|
4516027fdb | ||
|
|
e35f2ea3cd | ||
|
|
6b79fad626 | ||
|
|
ac311be430 | ||
|
|
4fb32bff5f | ||
|
|
5fda342a55 | ||
|
|
e23aab4710 | ||
|
|
3837d5dace | ||
|
|
f61e7cb1ed | ||
|
|
3de0c0e4ac | ||
|
|
63796d3feb | ||
|
|
6b07529300 | ||
|
|
e10676710c | ||
|
|
77f67c6666 | ||
|
|
bdbcdd61e1 | ||
|
|
4ab7ec754d | ||
|
|
20f98f48bc | ||
|
|
84e0502e50 | ||
|
|
2aa1b00dbb | ||
|
|
972078a514 | ||
|
|
be8382d25b | ||
|
|
8d46e88cd8 | ||
|
|
6b6b1b79ad | ||
|
|
e1fd40b34d | ||
|
|
bc1f8f97a8 | ||
|
|
b51705f458 | ||
|
|
aaed5f4797 | ||
|
|
a8eedef1d2 | ||
|
|
9407e21e1e | ||
|
|
ba6dcfd467 | ||
|
|
e2c1de5008 | ||
|
|
10b7403748 | ||
|
|
1ba924cc12 | ||
|
|
11eb034bd3 | ||
|
|
c3250e15cb | ||
|
|
8ff8a59b4c | ||
|
|
0c646d88b2 | ||
|
|
05670ea599 | ||
|
|
e25eb32885 | ||
|
|
250f75f084 | ||
|
|
cdd39e6777 | ||
|
|
281ed6766c | ||
|
|
cd78c89de1 | ||
|
|
c6c983e8f2 | ||
|
|
ef4d1ce54f | ||
|
|
b1177f4265 | ||
|
|
02d373e4a6 | ||
|
|
58c8608667 | ||
|
|
848110ac3e | ||
|
|
74d677cf09 | ||
|
|
f029c4eb4f | ||
|
|
838811f085 | ||
|
|
e212ec7ca3 | ||
|
|
6314a536af | ||
|
|
df33765ce0 | ||
|
|
2524333e79 | ||
|
|
cf81e815ee | ||
|
|
7bd7f1826c | ||
|
|
9ce7b528e3 | ||
|
|
db7b3cf0b5 | ||
|
|
201b30b6c4 | ||
|
|
36a6bcd1f5 | ||
|
|
20cfca5bb6 | ||
|
|
63fe4b15c8 | ||
|
|
aabc57a1f8 | ||
|
|
9a8eca0993 | ||
|
|
f8723d7e52 | ||
|
|
59bb5528ed | ||
|
|
247c10692a | ||
|
|
63bed3c127 | ||
|
|
ca96743bad | ||
|
|
525fb4de61 | ||
|
|
f294084dbc | ||
|
|
ca1327a9ae | ||
|
|
dcb1b0b3dc | ||
|
|
ec4b613498 | ||
|
|
c3f4eccfbc | ||
|
|
1aafe25a83 | ||
|
|
cc25ef0af0 | ||
|
|
5c221f4a14 | ||
|
|
03221fc645 | ||
|
|
febf81e597 | ||
|
|
447ec55822 | ||
|
|
eee1f49c4a | ||
|
|
140b903783 | ||
|
|
8361bc9f3a | ||
|
|
744290c228 | ||
|
|
20768df430 | ||
|
|
7ec7e8d432 | ||
|
|
7b657a85ba | ||
|
|
258699f1db | ||
|
|
0412f45323 | ||
|
|
997eb93cd9 | ||
|
|
b94192486b | ||
|
|
73bdd2c5bf | ||
|
|
56e9b54cd9 | ||
|
|
3308074f81 | ||
|
|
c2305034a1 | ||
|
|
d77b22be37 | ||
|
|
9717912ff7 | ||
|
|
cfa79c08b2 | ||
|
|
4f65f87ad6 | ||
|
|
aea0d21fd2 | ||
|
|
ba77b43364 | ||
|
|
7727eb58a8 | ||
|
|
dbd2e3f54b | ||
|
|
7ac6e07576 | ||
|
|
24ffd90fb4 | ||
|
|
011b680337 | ||
|
|
5328e07a93 | ||
|
|
2d07af7cc8 | ||
|
|
a40d2da2ab | ||
|
|
25ac101751 | ||
|
|
a666165a5e | ||
|
|
e24aedc6ac | ||
|
|
d10d69e44b | ||
|
|
af5c01ee3a | ||
|
|
bf350cddc8 | ||
|
|
9bc4d909b5 | ||
|
|
42236de5bd | ||
|
|
02e2fe2cc8 | ||
|
|
b75bcb90f4 | ||
|
|
56b88eb406 | ||
|
|
93741ea9ab | ||
|
|
f7509132fc | ||
|
|
2d0d62ec00 | ||
|
|
4e07a84102 | ||
|
|
32a048a879 | ||
|
|
caac28fcbc | ||
|
|
5b0bbf57c6 | ||
|
|
072af938c2 | ||
|
|
9e8202371e | ||
|
|
27dd253c5d | ||
|
|
8d651af2f8 | ||
|
|
6358312272 | ||
|
|
42c8367e13 | ||
|
|
c1e38b5e81 | ||
|
|
1b4ce24037 | ||
|
|
cf440750b6 | ||
|
|
30c480df36 | ||
|
|
9c3dbd39ef | ||
|
|
1af2f92828 | ||
|
|
45277bb00f | ||
|
|
10e21a3af9 | ||
|
|
19cbadd420 | ||
|
|
a28cbe52b9 | ||
|
|
37f1d64e46 | ||
|
|
7170325df5 | ||
|
|
c44d98da66 | ||
|
|
018410afb0 | ||
|
|
fc47238a7a | ||
|
|
9561b8a64e | ||
|
|
7b0e56b55f | ||
|
|
c6d5a79776 | ||
|
|
faa4cacd3e | ||
|
|
56e417eea1 | ||
|
|
5f02ec00f9 | ||
|
|
5ea35db922 | ||
|
|
5dcf26a56c | ||
|
|
35b598d10e | ||
|
|
5e7b27c4ef | ||
|
|
9ed408d35b | ||
|
|
6c782fe255 | ||
|
|
1689323dc3 | ||
|
|
a3c50a907a | ||
|
|
36a3792846 | ||
|
|
4cd0c0691a | ||
|
|
6ac98dcacd | ||
|
|
0a0d00930a | ||
|
|
28a0d041f9 | ||
|
|
85bb91a7ea | ||
|
|
6561e0abfa | ||
|
|
6715e61a68 | ||
|
|
a886b284b6 | ||
|
|
a349c82b6f | ||
|
|
1f4df0ebf4 | ||
|
|
0221e7bf93 | ||
|
|
f9cf14e7d8 | ||
|
|
7258e56a20 | ||
|
|
90bd495d44 | ||
|
|
6c216d6dfe | ||
|
|
e1f3fae6c7 | ||
|
|
29f126ca47 | ||
|
|
8b4b742466 | ||
|
|
57a9d362bc | ||
|
|
b7d54c2bea | ||
|
|
59f9833076 | ||
|
|
8e360fe53e | ||
|
|
afc5005382 | ||
|
|
3a531c6d2b | ||
|
|
f056ad6347 | ||
|
|
5c1342a663 | ||
|
|
dfe8a47a2a | ||
|
|
e293a439dd | ||
|
|
7e0027922a | ||
|
|
00b5302ba9 | ||
|
|
79488c4785 | ||
|
|
c3d0438250 | ||
|
|
2909d4636b | ||
|
|
a1ee8b6af4 | ||
|
|
cfe3b58f7f | ||
|
|
ff6b87ef5b | ||
|
|
8fbcfd0d5a | ||
|
|
347ba999b4 | ||
|
|
503bcf64c9 | ||
|
|
2a667470a1 | ||
|
|
c61165b840 | ||
|
|
3672189bc8 | ||
|
|
5b38c772fb | ||
|
|
f28bc4dd9c | ||
|
|
e16cc49a17 | ||
|
|
f686cc94fd | ||
|
|
d88b5a3b3e | ||
|
|
bccc5665f5 | ||
|
|
69ac9d39ad | ||
|
|
b5b6999bc9 | ||
|
|
7ddb3d2752 | ||
|
|
9febaf919c | ||
|
|
2225383485 | ||
|
|
e3e500326c | ||
|
|
b73570fe2a | ||
|
|
d1357875c9 | ||
|
|
037c7661ea | ||
|
|
5337ade3fb | ||
|
|
504ce5458f | ||
|
|
d8d3b60cbc | ||
|
|
0b0e7d5531 | ||
|
|
18cd9ab7ca | ||
|
|
1392b3b1eb | ||
|
|
cd93abfab1 | ||
|
|
9fede00949 | ||
|
|
6ddc3fec96 | ||
|
|
f1030f9b6f | ||
|
|
6a8ff22f96 | ||
|
|
1e82b79c16 | ||
|
|
d85bc90cbb | ||
|
|
fdce48376a | ||
|
|
58cc6b2e7d | ||
|
|
5ebad3cb70 | ||
|
|
d4757a0a74 | ||
|
|
0406a4b901 | ||
|
|
95684fbe3a | ||
|
|
a4f8155138 | ||
|
|
cddb1ba7f3 | ||
|
|
73b2930a0b | ||
|
|
e74519ca43 | ||
|
|
f75fad9c6a | ||
|
|
2d8805a49f | ||
|
|
fc3a19a816 | ||
|
|
e1b2d49341 | ||
|
|
2cb6890dac | ||
|
|
e6bef729ed | ||
|
|
1545f7a4ef | ||
|
|
3f9446a336 | ||
|
|
7b3ab90a95 | ||
|
|
636b264432 | ||
|
|
59fd6bf23d | ||
|
|
59b4bbcdaa | ||
|
|
a82bdd9f74 | ||
|
|
a4f10e7577 | ||
|
|
71f3231487 | ||
|
|
2133092402 | ||
|
|
20e47ab099 | ||
|
|
3e9c8c3ff8 | ||
|
|
731f331502 | ||
|
|
b15efb4d38 | ||
|
|
ccfb0df819 | ||
|
|
620ef9fc64 | ||
|
|
f799fc08f7 | ||
|
|
11a1ce4a6c | ||
|
|
9610a5a0dd | ||
|
|
0b39afcd18 | ||
|
|
abe53b8a8a | ||
|
|
bffdf77d9a | ||
|
|
31a7016c15 | ||
|
|
b92bd6aa0d | ||
|
|
ed4a6567c3 | ||
|
|
1988977d7c | ||
|
|
9f33bb4bb3 | ||
|
|
02a8141de2 | ||
|
|
c852b44dcd | ||
|
|
1a44b38308 | ||
|
|
743bf88d28 | ||
|
|
c0250c2c29 | ||
|
|
50990a8a01 | ||
|
|
03c12a65ac | ||
|
|
3f7967326b | ||
|
|
6d47ba30b9 | ||
|
|
c4459e2238 | ||
|
|
cba0d3f890 |
3
.gitmodules
vendored
@@ -1,3 +0,0 @@
|
||||
[submodule "interfaces/Config"]
|
||||
path = interfaces/Config
|
||||
url = https://github.com/thezoggy/sabnzbd-uni_Config.git
|
||||
@@ -1,5 +1,5 @@
|
||||
*******************************************
|
||||
*** This is SABnzbd 0.7.0 ***
|
||||
*** This is SABnzbd 0.7.9 ***
|
||||
*******************************************
|
||||
SABnzbd is an open-source cross-platform binary newsreader.
|
||||
It simplifies the process of downloading from Usenet dramatically,
|
||||
|
||||
280
CHANGELOG.txt
@@ -1,3 +1,283 @@
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.9Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix fatal error in decoder when encountering a malformed article
|
||||
- Fix compatibility with free.xsusenet.com
|
||||
- Small fix in smpl-black CSS
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.8Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix problem with %fn substitution in Sorting
|
||||
- Add special "wait_for_dfolder", enables waiting for external temp download folder
|
||||
- Work-around for servers that do not support STAT command
|
||||
- Removed articles are now listed seperately in download report
|
||||
- Add "abort" option to encryption detection
|
||||
- Fix missing Retry link for "Out of retention" jobs.
|
||||
- Option to abort download when it is clear that not enough data is available
|
||||
- Support "nzbname" parameter in addfile/addlocalfile api calls for
|
||||
ZIP files with a single NZB
|
||||
- Support NZB-1.1 meta data "password" and "category"
|
||||
- Don't retry an empty but correct NZB from an indexer
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.7Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Windows/OSX: Update unrar to 4.20
|
||||
- Fix some issues with orphaned items
|
||||
- Generic sort didn't always rename media files in multi-part jobs properly
|
||||
- Optional web-ui watchdog
|
||||
- Always show RSS items in the same order as the original RSS feed
|
||||
- Remove unusable folders from folder selector (Plush skin)
|
||||
- Remove newzbin support
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.6Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Recursive scanning when re-queuing downloaded NZB files
|
||||
- Log "User-Agent" header of API calls
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.6Beta2 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- A damaged smallest par2 can block fetching of more par2 files
|
||||
- Fix evaluation of schedules at startup
|
||||
- Make check for running SABnzbd instance more robust
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.6Beta1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Handle par2 sets that were renamed after creation
|
||||
- Prevent blocking assembly of completed files, ( this resulted in
|
||||
excessive CPU and memory usage)
|
||||
- Fix speed issues with some Usenet servers due to unreachable IPv6 addresses
|
||||
- Fix issues with SFV-base checks
|
||||
- Prevent crash on Unix-Pythons that don't have the os.getloadavg() function
|
||||
- Successfully pre-checked job lost its attributes when those were changed during check
|
||||
- Remove version check when looking for a running instance of SABnzbd
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.5Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Add missing %dn formula to Generic Sort
|
||||
- Improve RSS logging
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.5RC1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Prevent stuck jobs at end of pre-check.
|
||||
- Fix issues with accented and special characters in names of downloaded files.
|
||||
- Adjust nzbmatrix category table.
|
||||
- Add 'prio_sort_list' special
|
||||
- Add special option 'empty_postproc'.
|
||||
- Prevent CherryPy crash when reading a cookie from another app which has a non-standard name.
|
||||
- Prevent crash when trying to open non-existing "complete" folder from Windows System-tray icon.
|
||||
- Fix problem with "Read" button when RSS feed name contains "&".
|
||||
- Prevent unusual SFV files from crashing post-processing.
|
||||
- OSX: Retina compatible menu-bar icons.
|
||||
- Don't show speed and ETA when download is paused during post-processing
|
||||
- Prevent soft-crash when api-function "addfile" is called without parameters.
|
||||
- Add news channel frame
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.4Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Pre-queue script no longer got the show/season/episode information.
|
||||
- Prevent crash on startup when a fully downloaded job is still in download queue.
|
||||
- New RSS feed should no longer be considered new after first, but empty readout.
|
||||
- Make "auth" call backward-compatible with 0.6.x releases.
|
||||
- Config->Notifications: email and growl server addresses should not be marked as "url" type.
|
||||
- OSX: fix top menu queue info so that it shows total queue size
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.4RC2 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Pre-check failed to consider extra par2 files
|
||||
- Fixed unjustified warning that can occur with OSX Growl 2.0
|
||||
- Show memory usage on Linux systems
|
||||
- Fix incorrect end-of-month quota reset
|
||||
- Fix UI refresh issue when using Safari on iOS6
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.4RC1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Remove potential queue stalling when downloading extra par2 files
|
||||
- Make Windows version less eager to use par2-classic
|
||||
- Fixed DMG images
|
||||
- Add missing encoding directive to Plush and Classic skins
|
||||
- Prevent oversized data in API-call "history"
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.4Beta3 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- All three OSX build in one DMG again
|
||||
- Minor bugfixes
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.4Beta2 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix failure to fetch more par2-files for posts with badly formatted subject lines
|
||||
- After successful pre-check, preserve a job's position in the queue
|
||||
- Restore SABnzbd icon for Growl
|
||||
- Fix "check new releases" option in Config skin
|
||||
- Separate DMG files for OSX Leopard/SL, Lion and MLion
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.4Beta1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- OSX Mountain Lion Notification Center support
|
||||
- OSX Mountain Lion improved "keep awake" support
|
||||
- OSX: separate builds: one for Mountain Lion and one for all others
|
||||
- OSX removed 64bit code
|
||||
- Scheduler: action can now run on multiple weekdays
|
||||
- Scheduler: add "remove failed jobs" action
|
||||
- Special option: rss_odd_titles (see Wiki)
|
||||
- Support for HTTPS chain files (needed when you buy your own certificate)
|
||||
- Prevent jobs from showing up in queue and history simultaneously
|
||||
- Add parameter 'pp_active' to history elements in qstatus API call
|
||||
- Fix some minor par2 handling bugs
|
||||
- Prevent potential crash when an actively downloading job is deleted from the queue
|
||||
- Special option: 'overwrite_files' (See Wiki)
|
||||
- Don't try an SFV check when a retried job was already successfully verified by par2
|
||||
- Enable compression of API call results
|
||||
- Log failed attempts to log in to the Web UI
|
||||
- A job with "forced" priority should keep that when fetching more par2 files
|
||||
- Updated translations
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.3Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Rename Special "random_server_ip" to "randomize_server_ip" so that we
|
||||
can force the default to "Off". "On" kills speed on some servers.
|
||||
- Ignore pseudo NZB files that start with a period in the name
|
||||
- SFV failure now listed in History instead of issuing warnings
|
||||
- Translation updates
|
||||
- "502" errors about payments/credits will now block a server
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.3Beta2 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Try to keep OSX Mountain Lion awake as long as downloading/postprocessing runs
|
||||
- Prevent queue deadlock in case of fatally damaged par2 files
|
||||
- Add RSS filter-enable checkboxes to Plush, Smpl and Classic skins
|
||||
- Fix problem with saving modified paramters of an already enabled server
|
||||
- Extend "check new release" option with test releases
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.3Beta1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Correct several errors in Sort function
|
||||
- Improve organization of Config->Servers
|
||||
- Support for nzbxxx.com
|
||||
- Make detection of samples less aggressive
|
||||
- Some minor corrections
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.2Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix for NZB-icon issue when 0.7.0 was previously installed
|
||||
- Check validity of totals9.sab file
|
||||
- Fix startup problem when localhost has unexpected order of IP addresses
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.2RC2 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Improve support for nzbsrus.com
|
||||
- Don't try to show NZB age when not known yet
|
||||
- Prevent systems with unresolvable hostnames from always using 0.0.0.0
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.2RC1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix fatal error in nzbsrus.com support
|
||||
- Initial "quota left" was not set correctly when enabling quota
|
||||
- Report incorrect RSS filter expressions (instead of aborting analysis)
|
||||
- Improve detection of invalid articles (so that backup server will be tried)
|
||||
- Windows installer: improve NZB association so that a reboot isn't needed
|
||||
- Windows installer: don't remove settimngs by default when uninstalling
|
||||
- Fix sorting of rar files in job so that .rar preceeds .r00
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.1Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Disable VC90 check in Windows Installer as long as we're still on Python 2.5
|
||||
- Windows: make sure \\server\share notation is never seen as a relative path
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.1RC5 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix signing of OSX DMG
|
||||
- Fix endless par2-fetch loop after retrying failed job
|
||||
- Don't send "bad fetch" email when emailing is off
|
||||
- Add some support for nzbrus.com's non-VIP limiting
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.1RC4 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix failure to grab NZBs from indexers that send compressed files.
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.1RC3 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fixed stalling par2 fetches (after first verification run)
|
||||
- Fixed retry behaviour of NZB fetching from URL
|
||||
and add handling of nzbsrus.com error codes
|
||||
- Make sure that all malformed articles are retried on another server
|
||||
- Add no_ipv6 option that suppresses listing on ::1
|
||||
(to be used if your system cannot handle that)
|
||||
- Prevent crash in QuickCheck when expected par2 file wasn't downloaded
|
||||
- Verification/repair would not be executed properly when one more RAR files
|
||||
missed their first article.
|
||||
- API calls "addurl" and "addid" (newzbin) can be used interchangeably
|
||||
(Fixes a problem in Qouch)
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.1RC2 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Improved backup of sabnzbd.ini file
|
||||
Will use backup when original is gone or become corrupt
|
||||
- Windows: Using ::1 as single webhost address would start IE instead of default browser
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.1RC1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Plush skin: fix problems with pull-down menus in Mobile Safari
|
||||
- On some Linux and OSX systems using localhost would still make SABnzbd
|
||||
give access to other computers
|
||||
- Windows: the installer did not set an icon when associating NZB files with SABnzbd
|
||||
- Fix problem that the Opera browser had with Config->Servers
|
||||
- Retry a few times when accessing a mounted drive to create the
|
||||
final destination folder
|
||||
- Reduce load caused by WinTray and OSX topmenu
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0Final by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Updated translations
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0RC2 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Suppress permission errors on paths containing ".AppleDouble" or ".DS_Store"
|
||||
(Required for NAS systems that support Apple AFP shares)
|
||||
- OSX/Windows: Set article cache to 200M when not already set.
|
||||
- Pre-check: lower default minimum completion rate to 100.2%
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0RC1 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix for rare crash in par2 fetching
|
||||
- Another /nomedia fix
|
||||
- Quota reset wasn't done when quota-reset-time was passed while SABnzbd wasn't running.
|
||||
- Pre-check: required ratio for NZB without par2 files should be 100%
|
||||
and not the "safe" ratio
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0Beta8 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Disabled the .nomedia marker file feature.
|
||||
Those who want to try it, use the "nomedia_marker" setting in Config->Special
|
||||
It remains an experimental feature without guarantees
|
||||
- Add missing info in email about failed pre-check
|
||||
- Updated translations
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0Beta7 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Fix for .nomedia files not being deleted
|
||||
- Fix NZB re-queueing (due to .nomedia remaining)
|
||||
- Polish was missing in Windows installer and Dutch was incorrect
|
||||
- When Sort renames auxillirary files, it should disregard case
|
||||
- Fix crash in Wizard on some Linux systems
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0Beta6 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Upgrade unzip for Windows to 6.00 (supports ZIPs above 2G)
|
||||
- Lower threshold for pre-check to 100.5%
|
||||
- Fix removal of .nomedia file when using Sorting
|
||||
- Add Polish translation (using reduced character set)
|
||||
- Extension-based cleanup list now also removes extension-only files like ".sfv".
|
||||
- Several small issues
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0Beta5 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
- Solved serious connection problem with some providers
|
||||
- Windows Tray has the "restart" entries no under a Troubleshoot menu
|
||||
- Fix newzbin entries in History's "Source" field
|
||||
- During unpacking the destination folder will contain a ".nomedia" file
|
||||
which will keep mediaplayers temporarily from indexing
|
||||
- Pre-check jobs now require 101% completion rate (with a "special" parameter)
|
||||
- Unified OSX DMG
|
||||
-------------------------------------------------------------------------------
|
||||
0.7.0Beta4 by The SABnzbd-Team
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
|
||||
(c) Copyright 2007-2012 by "The SABnzbd-team" <team@sabnzbd.org>
|
||||
(c) Copyright 2007-2013 by "The SABnzbd-team" <team@sabnzbd.org>
|
||||
|
||||
The SABnzbd-team is:
|
||||
|
||||
@@ -26,6 +26,7 @@ The main contributors and moderators of the translations
|
||||
Spanish: Syquus
|
||||
Portuguese (Brazil): lrrosa
|
||||
Russian: Pavel Maryanov
|
||||
Polish: Tomasz 'Zen' Napierala
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
|
||||
20
INSTALL.txt
@@ -1,10 +1,10 @@
|
||||
SABnzbd 0.7.0
|
||||
SABnzbd 0.7.9
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
0) LICENSE
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
(c) Copyright 2007-2012 by "The SABnzbd-team" <team@sabnzbd.org>
|
||||
(c) Copyright 2007-2013 by "The SABnzbd-team" <team@sabnzbd.org>
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
@@ -42,14 +42,17 @@ Use the "Help" button in the web-interface to be directed to the Help Wiki.
|
||||
-------------------------------------------------------------------------------
|
||||
3) INSTALL pre-built OSX binaries
|
||||
-------------------------------------------------------------------------------
|
||||
Download teh DMG file, mount and drag the SABnzbd icon to Programs.
|
||||
Download the DMG file, mount and drag the SABnzbd icon to Programs.
|
||||
Just like you do with so many apps.
|
||||
Make sure you pick the right folder, depending on your OSX version.
|
||||
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
4) INSTALL with only sources
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
You need to have Python installed and some modules.
|
||||
You need to have Python installed plus some non-standard Python modules
|
||||
and a few tools.
|
||||
|
||||
Unix/Linux/OSX
|
||||
Python-2.5, 2.6 or 2.7 http://www.python.org
|
||||
@@ -57,23 +60,22 @@ Unix/Linux/OSX
|
||||
OSX Leopard/SnowLeopard
|
||||
Python 2.6 http://www.activestate.com
|
||||
|
||||
OSX Lion Apple Python 2.7 (included in OSX)
|
||||
OSX Lion/MountainLion
|
||||
Apple Python 2.7 Included in OSX (default)
|
||||
|
||||
Windows
|
||||
Python-2.7.latest http://www.activestate.com
|
||||
|
||||
Essential modules
|
||||
cheetah-2.0.1+ http://www.cheetahtemplate.org/ (or use "pypm install cheetah")
|
||||
yenc module >= 0.3 http://sabnzbd.sourceforge.net/yenc-0.3.tar.gz
|
||||
http://sabnzbd.sourceforge.net/yenc-0.3-w32fixed.zip (Win32-only)
|
||||
par2cmdline >= 0.4 http://parchive.sourceforge.net/
|
||||
http://chuchusoft.com/par2_tbb/index.html (multi-core)
|
||||
|
||||
Optional modules
|
||||
unrar >= 3.90+ http://www.rarlab.com/rar_add.htm
|
||||
unzip >= 5.52 http://www.info-zip.org/
|
||||
gnu gettext http://www.gnu.org/software/gettext/
|
||||
gntp https://github.com/kfdm/gntp/ (or use "pypm install gntp")
|
||||
yenc module >= 0.3 http://sabnzbd.sourceforge.net/yenc-0.3.tar.gz
|
||||
http://sabnzbd.sourceforge.net/yenc-0.3-w32fixed.zip (Win32-only)
|
||||
|
||||
Optional modules Windows
|
||||
pyopenssl >= 0.11 http://pypi.python.org/pypi/pyOpenSSL
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
(c) Copyright 2007-2012 by "The SABnzbd-team" <team@sabnzbd.org>
|
||||
(c) Copyright 2007-2013 by "The SABnzbd-team" <team@sabnzbd.org>
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
|
||||
!include "MUI2.nsh"
|
||||
!include "registerExtension.nsh"
|
||||
!include "FileFunc.nsh"
|
||||
!include "LogicLib.nsh"
|
||||
!include "WinVer.nsh"
|
||||
!include "WinSxSQuery.nsh"
|
||||
@@ -40,6 +41,7 @@
|
||||
Delete "${idir}\email\email-sv.tmpl"
|
||||
Delete "${idir}\email\email-da.tmpl"
|
||||
Delete "${idir}\email\email-nb.tmpl"
|
||||
Delete "${idir}\email\email-pl.tmpl"
|
||||
Delete "${idir}\email\email-ro.tmpl"
|
||||
Delete "${idir}\email\email-sr.tmpl"
|
||||
Delete "${idir}\email\email-es.tmpl"
|
||||
@@ -49,6 +51,7 @@
|
||||
Delete "${idir}\email\rss-de.tmpl"
|
||||
Delete "${idir}\email\rss-en.tmpl"
|
||||
Delete "${idir}\email\rss-nl.tmpl"
|
||||
Delete "${idir}\email\rss-pl.tmpl"
|
||||
Delete "${idir}\email\rss-fr.tmpl"
|
||||
Delete "${idir}\email\rss-sv.tmpl"
|
||||
Delete "${idir}\email\rss-da.tmpl"
|
||||
@@ -65,6 +68,7 @@
|
||||
Delete "${idir}\email\badfetch-fr.tmpl"
|
||||
Delete "${idir}\email\badfetch-nb.tmpl"
|
||||
Delete "${idir}\email\badfetch-nl.tmpl"
|
||||
Delete "${idir}\email\badfetch-pl.tmpl"
|
||||
Delete "${idir}\email\badfetch-ro.tmpl"
|
||||
Delete "${idir}\email\badfetch-sr.tmpl"
|
||||
Delete "${idir}\email\badfetch-sv.tmpl"
|
||||
@@ -81,6 +85,7 @@
|
||||
RMDir /r "${idir}\interfaces\wizard"
|
||||
RMDir /r "${idir}\interfaces\Config"
|
||||
RMDir "${idir}\interfaces"
|
||||
RMDir /r "${idir}\win\curl"
|
||||
RMDir /r "${idir}\win\par2"
|
||||
RMDir /r "${idir}\win\unrar"
|
||||
RMDir /r "${idir}\win\unzip"
|
||||
@@ -114,6 +119,7 @@
|
||||
Delete "${idir}\IMPORTANT_MESSAGE.txt"
|
||||
Delete "${idir}\SABnzbd-console.exe"
|
||||
Delete "${idir}\SABnzbd.exe"
|
||||
Delete "${idir}\SABnzbd.exe.log"
|
||||
Delete "${idir}\SABnzbd-helper.exe"
|
||||
Delete "${idir}\SABnzbd-service.exe"
|
||||
Delete "${idir}\Sample-PostProc.cmd"
|
||||
@@ -209,6 +215,7 @@
|
||||
!insertmacro MUI_LANGUAGE "French"
|
||||
!insertmacro MUI_LANGUAGE "German"
|
||||
!insertmacro MUI_LANGUAGE "Dutch"
|
||||
!insertmacro MUI_LANGUAGE "Polish"
|
||||
!insertmacro MUI_LANGUAGE "Swedish"
|
||||
!insertmacro MUI_LANGUAGE "Danish"
|
||||
!insertmacro MUI_LANGUAGE "NORWEGIAN"
|
||||
@@ -239,6 +246,7 @@ Function .onInit
|
||||
;--------------------------------
|
||||
;make sure that the requires MS Runtimes are installed
|
||||
;
|
||||
goto nodownload ; Not needed while still using Python25
|
||||
runtime_loop:
|
||||
push 'msvcr90.dll'
|
||||
push 'Microsoft.VC90.CRT,version="9.0.21022.8",type="win32",processorArchitecture="x86",publicKeyToken="1fc8b3b9a1e18e3b"'
|
||||
@@ -291,7 +299,7 @@ SetOutPath "$INSTDIR"
|
||||
;------------------------------------------------------------------
|
||||
; Make sure old versions are gone
|
||||
IfFileExists $INSTDIR\sabnzbd.exe 0 endWarnExist
|
||||
IfFileExists $INSTDIR\python25.dll 0 endWarnExist
|
||||
IfFileExists $INSTDIR\python27.dll 0 endWarnExist
|
||||
MessageBox MB_OKCANCEL|MB_ICONEXCLAMATION "$(MsgRemoveOld)$\n$\n$(MsgRemoveOld2)" IDOK uninst
|
||||
Abort
|
||||
uninst:
|
||||
@@ -312,7 +320,7 @@ WriteRegStr HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninst
|
||||
WriteRegStr HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninstall\SABnzbd" "URLUpdateInfo" 'http://sabnzbd.org/'
|
||||
WriteRegStr HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninstall\SABnzbd" "Comments" 'The automated Usenet download tool'
|
||||
WriteRegStr HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninstall\SABnzbd" "DisplayIcon" '$INSTDIR\interfaces\Classic\templates\static\images\favicon.ico'
|
||||
WriteRegDWORD HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninstall\SABnzbd" "EstimatedSize" 18400
|
||||
WriteRegDWORD HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninstall\SABnzbd" "EstimatedSize" 25674
|
||||
WriteRegDWORD HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninstall\SABnzbd" "NoRepair" -1
|
||||
WriteRegDWORD HKEY_LOCAL_MACHINE "Software\Microsoft\Windows\CurrentVersion\Uninstall\SABnzbd" "NoModify" -1
|
||||
; write out uninstaller
|
||||
@@ -343,8 +351,8 @@ Section $(MsgIcon) desktop
|
||||
SectionEnd ; end of desktop icon section
|
||||
|
||||
Section /o $(MsgAssoc) assoc
|
||||
${registerExtension} "$INSTDIR\nzb.ico" "$INSTDIR\SABnzbd.exe" ".nzb" "NZB File"
|
||||
;${registerExtension} "$INSTDIR\SABnzbd.exe" ".nzb" "NZB File"
|
||||
${registerExtension} "$INSTDIR\icons\nzb.ico" "$INSTDIR\SABnzbd.exe" ".nzb" "NZB File"
|
||||
${RefreshShellIcons}
|
||||
SectionEnd ; end of file association section
|
||||
|
||||
; begin uninstall settings/section
|
||||
@@ -400,11 +408,11 @@ Section "un.$(MsgDelProgram)" Uninstall
|
||||
DeleteRegKey HKEY_CURRENT_USER "Software\SABnzbd"
|
||||
|
||||
${unregisterExtension} ".nzb" "NZB File"
|
||||
|
||||
${RefreshShellIcons}
|
||||
|
||||
SectionEnd ; end of uninstall section
|
||||
|
||||
Section "un.$(MsgDelSettings)" DelSettings
|
||||
Section /o "un.$(MsgDelSettings)" DelSettings
|
||||
DetailPrint "Uninstall settings $LOCALAPPDATA"
|
||||
Delete "$LOCALAPPDATA\sabnzbd\sabnzbd.ini"
|
||||
RMDir /r "$LOCALAPPDATA\sabnzbd"
|
||||
|
||||
6
PKG-INFO
@@ -1,8 +1,8 @@
|
||||
Metadata-Version: 1.0
|
||||
Name: SABnzbd
|
||||
Version: 0.7.0Beta4
|
||||
Summary: SABnzbd-0.7.0Beta4
|
||||
Home-page: http://sourceforge.net/projects/sabnzbdplus
|
||||
Version: 0.7.9
|
||||
Summary: SABnzbd-0.7.9
|
||||
Home-page: http://sabnzbd.org
|
||||
Author: The SABnzbd Team
|
||||
Author-email: team@sabnzbd.org
|
||||
License: GNU General Public License 2 (GPL2 or later)
|
||||
|
||||
78
README.mkd
Normal file
@@ -0,0 +1,78 @@
|
||||
Release Notes - SABnzbd 0.7.9
|
||||
===============================
|
||||
|
||||
## Bug fix 0.7.9
|
||||
- Fix fatal error when encountering a malformed article
|
||||
|
||||
## Features (0.7.8)
|
||||
- Use "category" and "password" meta-data in NZB files
|
||||
(Provided by some indexers)
|
||||
- Option to abort download when it is clear that not enough data is available
|
||||
(For removed posts it will be faster than pre-download check)
|
||||
- Add "Abort" option for encryption detection
|
||||
- Removed articles are now listed separately in download report
|
||||
- Special option "wait_for_dfolder", enables waiting for external temp download folder at startup
|
||||
|
||||
## Bug fixes (0.7.8)
|
||||
- Fix problem with %fn substitution in Sorting
|
||||
- Pre-download check did not work with all servers
|
||||
- Fix missing Retry link for "Out of retention" jobs.
|
||||
- API function "addfile" now accepts "nzbname" parameter for ZIP/RAR files with one NZB.
|
||||
- Prevent retries when an NZB with just samples is retrieved from an indexer
|
||||
(and you had the "do not download samples" option enabled).
|
||||
|
||||
## What's new in 0.7.0
|
||||
|
||||
- Download quota management
|
||||
- Windows: simple system tray menu
|
||||
- Multi-platform Growl support
|
||||
- NotifyOSD support for Linux distros that have it
|
||||
- Option to set maximum number of retries for servers (prevents deadlock)
|
||||
- Pre-download check to estimate completeness (reliability is limited)
|
||||
- Prevent partial downloading of par2 files that are not needed yet
|
||||
- Config->Special for settings previously only available in the sabnzbd.ini file
|
||||
- For Usenet servers with multiple IP addresses, pick a random one per connection
|
||||
- Add pseudo-priority "Stop" that will send the job immediately to the post-processing queue
|
||||
- Allow jobs still waiting for post-processing to be deleted too
|
||||
- More persistent retries for unreliable indexers
|
||||
- Single Configuration skin for all others skins (there is an option for the old style)
|
||||
- Config->Special for settings that were previously only changeable in the sabnzbd.ini file
|
||||
- Add Spanish, Portuguese (Brazil) and Polish translations
|
||||
- Individual RSS filter toggle
|
||||
- Unified OSX DMG
|
||||
|
||||
|
||||
## About
|
||||
SABnzbd is an open-source cross-platform binary newsreader.
|
||||
It simplifies the process of downloading from Usenet dramatically,
|
||||
thanks to its web-based user interface and advanced
|
||||
built-in post-processing options that automatically verify, repair,
|
||||
extract and clean up posts downloaded from Usenet.
|
||||
|
||||
(c) Copyright 2007-2013 by "The SABnzbd-team" \<team@sabnzbd.org\>
|
||||
|
||||
|
||||
### IMPORTANT INFORMATION about release 0.7.x
|
||||
<http://wiki.sabnzbd.org/introducing-0-7-0>
|
||||
|
||||
### Known problems and solutions
|
||||
- Read the file "ISSUES.txt"
|
||||
|
||||
### Upgrading from 0.6.x
|
||||
- Stop SABnzbd
|
||||
- Install new version
|
||||
- Start SABnzbd
|
||||
|
||||
### Upgrading from 0.5.x
|
||||
- Stop SABnzbd
|
||||
- Install new version
|
||||
- Start SABnzbd.
|
||||
|
||||
The organization of the download queue is different from 0.5.x.
|
||||
0.7.x will finish downloading an existing queue, but you
|
||||
cannot go back to an older version without losing your queue.
|
||||
Also, your sabnzbd.ini file will be upgraded, making it
|
||||
incompatible with release 0.5.x
|
||||
|
||||
### Upgrading from 0.4.x
|
||||
Download your current queue before upgrading.
|
||||
103
README.rtf
@@ -1,103 +0,0 @@
|
||||
{\rtf1\ansi\ansicpg1252\cocoartf1038\cocoasubrtf360
|
||||
{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
|
||||
{\colortbl;\red255\green255\blue255;}
|
||||
\paperw11900\paperh16840\vieww16360\viewh15680\viewkind0
|
||||
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\ql\qnatural
|
||||
|
||||
\f0\b\fs48 \cf0 SABnzbd 0.7.0Beta4\
|
||||
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\ql\qnatural\pardirnatural
|
||||
|
||||
\b0\fs26 \cf0 \
|
||||
|
||||
\b What's new
|
||||
\b0 \
|
||||
- Download quota management\
|
||||
- Windows: simple system tray menu\
|
||||
- Multi-platform Growl support\
|
||||
- NotifyOSD support for Linux distros that have it\
|
||||
- Option to set maximum number of retries for servers (prevents deadlock)\
|
||||
- Pre-download check to estimate completeness (reliability is limited)\
|
||||
- Prevent partial downloading of par2 files that are not needed yet\
|
||||
- Config->Special for settings previously only available in the sabnzbd.ini file\
|
||||
- For Usenet servers with multiple IP addresses, pick a random one per connection\
|
||||
- Add pseudo-priority "Stop" that will send the job immediately to the post-processing queue\
|
||||
- Allow jobs still waiting for post-processing to be deleted too\
|
||||
- More persistent retries for unreliable indexers\
|
||||
- Single Configuration skin for all others skins (there is an option for the old style)\
|
||||
- Config->Special for settings that were previously only changeable in the sabnzbd.ini file\
|
||||
- Add Spanish and Portuguese (Brazil) translations\
|
||||
- Individual RSS filter toggle\
|
||||
\
|
||||
For problems fixed in Beta4, see CHANGELOG.txt\
|
||||
\
|
||||
\b About
|
||||
\b0 \
|
||||
SABnzbd is an open-source cross-platform binary newsreader.\
|
||||
It simplifies the process of downloading from Usenet dramatically,\
|
||||
thanks to its friendly web-based user interface and advanced\
|
||||
built-in post-processing options that automatically verify, repair,\
|
||||
extract and clean up posts downloaded from Usenet.\
|
||||
SABnzbd also has a fully customizable user interface,\
|
||||
and offers a complete API for third-party applications to hook into.\
|
||||
\
|
||||
(c) Copyright 2007-2012 by "The SABnzbd-team" <team@sabnzbd.org>\
|
||||
\
|
||||
There is an extensive Wiki on the use of SABnzbd.\
|
||||
{\field{\*\fldinst{HYPERLINK "http://wiki.sabnzbd.org/"}}{\fldrslt http://wiki.sabnzbd.org/}}\
|
||||
\
|
||||
|
||||
\b IMPORTANT INFORMATION
|
||||
\b0 about release 0.6.0:\
|
||||
{\field{\*\fldinst{HYPERLINK "http://wiki.sabnzbd.org/introducing-0-6-0"}}{\fldrslt http://wiki.sabnzbd.org/introducing-0-6-0}}\
|
||||
\
|
||||
|
||||
\b Known problems and solutions\
|
||||
|
||||
\b0 Read the file"ISSUES.txt"
|
||||
\b \
|
||||
|
||||
\b0 \
|
||||
\
|
||||
|
||||
\b\fs40 Upgrading from 0.6.x
|
||||
\b0\fs26 \
|
||||
Stop SABnzbd.\
|
||||
Install new version\
|
||||
Start SABnzbd.\
|
||||
\
|
||||
|
||||
\b\fs40 Upgrading from 0.5.x
|
||||
\b0\fs26 \
|
||||
Stop SABnzbd.\
|
||||
Uninstall current version, keeping the data.\
|
||||
Install new version\
|
||||
Start SABnzbd.\
|
||||
\
|
||||
The organization of the download queue is different from 0.5.x.\
|
||||
0.6.x will finish downloading an existing queue, but you\
|
||||
cannot go back to an older version without losing your queue.\
|
||||
Also, your sabnzbd.ini file will be upgraded, making it\
|
||||
incompatible with release 0.5.x\
|
||||
\
|
||||
|
||||
\b\fs40 \
|
||||
Upgrading from 0.4.x
|
||||
\b0\fs26 \
|
||||
\
|
||||
|
||||
\b PLEASE DOWNLOAD YOUR CURRENT QUEUE BEFORE UPGRADING
|
||||
\b0 \
|
||||
\
|
||||
When upgrading from a 0.4.x release such as 0.4.12 your old settings will be kept.\
|
||||
You will however be given a fresh queue and history. If you have items in your queue\
|
||||
from the older version of SABnzbd, you can either re-import the nzb files if you kept\
|
||||
an nzb backup folder, or temporarily go back to 0.4.x until your queue is complete.\
|
||||
The history is now stored in a better format meaning future upgrades should be backwards\
|
||||
compatible.\
|
||||
\
|
||||
\
|
||||
|
||||
\b\fs40 Changes since 0.5.6
|
||||
\b0\fs26 \
|
||||
See: {\field{\*\fldinst{HYPERLINK "http://wiki.sabnzbd.org/introducing-0-6-0"}}{\fldrslt http://wiki.sabnzbd.org/introducing-0-6-0}}\
|
||||
}
|
||||
32
README.txt
@@ -1,32 +0,0 @@
|
||||
************************ SABnzbd 0.7.0Beta4 ************************
|
||||
|
||||
What's new:
|
||||
|
||||
- Download quota management
|
||||
- Windows: simple system tray menu
|
||||
- Multi-platform Growl support
|
||||
- NotifyOSD support for Linux distros that have it
|
||||
- Option to set maximum number of retries for servers (prevents deadlock)
|
||||
- Pre-download check to estimate completeness (reliability is limited)
|
||||
- Prevent partial downloading of par2 files that are not needed yet
|
||||
- Config->Special for settings previously only available in the sabnzbd.ini file
|
||||
- For Usenet servers with multiple IP addresses, pick a random one per connection
|
||||
- Add pseudo-priority "Stop" that will send the job immediately to the post-processing queue
|
||||
- Allow jobs still waiting for post-processing to be deleted too
|
||||
- More persistent retries for unreliable indexers
|
||||
- Single Configuration skin for all others skins (there is an option for the old style)
|
||||
- Config->Special for settings that were previously only changeable in the sabnzbd.ini file
|
||||
- Add Spanish and Portuguese (Brazil) translations
|
||||
- Individual RSS filter toggle
|
||||
|
||||
For problems fixed in Beta4, see CHANGELOG.txt
|
||||
|
||||
|
||||
About:
|
||||
SABnzbd is an open-source cross-platform binary newsreader.
|
||||
It simplifies the process of downloading from Usenet dramatically,
|
||||
thanks to its friendly web-based user interface and advanced
|
||||
built-in post-processing options that automatically verify, repair,
|
||||
extract and clean up posts downloaded from Usenet.
|
||||
|
||||
(c) Copyright 2007-2012 by "The SABnzbd-team" <team@sabnzbd.org>
|
||||
135
SABnzbd.py
@@ -1,5 +1,5 @@
|
||||
#!/usr/bin/python -OO
|
||||
# Copyright 2008-2012 The SABnzbd-Team <team@sabnzbd.org>
|
||||
# Copyright 2008-2013 The SABnzbd-Team <team@sabnzbd.org>
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU General Public License
|
||||
@@ -16,8 +16,8 @@
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
import sys
|
||||
if sys.version_info < (2,5):
|
||||
print "Sorry, requires Python 2.5 or higher."
|
||||
if sys.version_info < (2, 5):
|
||||
print "Sorry, requires Python 2.5, 2.6 or 2.7."
|
||||
sys.exit(1)
|
||||
|
||||
import logging
|
||||
@@ -28,6 +28,7 @@ import signal
|
||||
import socket
|
||||
import platform
|
||||
import time
|
||||
import re
|
||||
|
||||
try:
|
||||
import Cheetah
|
||||
@@ -253,12 +254,13 @@ def print_help():
|
||||
print " --log-all Log all article handling (for developers)"
|
||||
print " --console Force console logging for OSX app"
|
||||
print " --new Run a new instance of SABnzbd"
|
||||
print " --no_ipv6 Do not listen on IPv6 address [::1]"
|
||||
|
||||
def print_version():
|
||||
print """
|
||||
%s-%s
|
||||
|
||||
Copyright (C) 2008-2012, The SABnzbd-Team <team@sabnzbd.org>
|
||||
Copyright (C) 2008-2013, The SABnzbd-Team <team@sabnzbd.org>
|
||||
SABnzbd comes with ABSOLUTELY NO WARRANTY.
|
||||
This is free software, and you are welcome to redistribute it
|
||||
under certain conditions. It is licensed under the
|
||||
@@ -524,32 +526,26 @@ def all_localhosts():
|
||||
return ips
|
||||
|
||||
|
||||
def ipv_localhost(v):
|
||||
""" Return True if localhost resolves to some IPV4 ('4') or IPV6 ('6') address
|
||||
def check_resolve(host):
|
||||
""" Return True if 'host' resolves
|
||||
"""
|
||||
try:
|
||||
info = socket.getaddrinfo('localhost', None)
|
||||
info = socket.getaddrinfo(host, None)
|
||||
except:
|
||||
# localhost does not resolve
|
||||
# Does not resolve
|
||||
return False
|
||||
for item in info:
|
||||
item = item[4][0]
|
||||
if v == '4' and ':' not in item:
|
||||
return True
|
||||
elif v == '6' and ':' in item:
|
||||
return True
|
||||
return False
|
||||
return True
|
||||
|
||||
#------------------------------------------------------------------------------
|
||||
def get_webhost(cherryhost, cherryport, https_port):
|
||||
""" Determine the webhost address and port,
|
||||
return (host, port, browserhost)
|
||||
"""
|
||||
if cherryhost == '0.0.0.0' and not ipv_localhost('4'):
|
||||
if cherryhost == '0.0.0.0' and not check_resolve('127.0.0.1'):
|
||||
cherryhost = ''
|
||||
elif cherryhost == '::' and not ipv_localhost('6'):
|
||||
elif cherryhost == '::' and not check_resolve('::1'):
|
||||
cherryhost = ''
|
||||
|
||||
|
||||
if cherryhost is None:
|
||||
cherryhost = sabnzbd.cfg.cherryhost()
|
||||
else:
|
||||
@@ -562,9 +558,18 @@ def get_webhost(cherryhost, cherryport, https_port):
|
||||
try:
|
||||
info = socket.getaddrinfo(socket.gethostname(), None)
|
||||
except:
|
||||
# Hostname does not resolve, use 0.0.0.0
|
||||
cherryhost = '0.0.0.0'
|
||||
info = socket.getaddrinfo(localhost, None)
|
||||
# Hostname does not resolve
|
||||
try:
|
||||
# Valid user defined name?
|
||||
info = socket.getaddrinfo(cherryhost, None)
|
||||
except:
|
||||
if cherryhost not in ('localhost', '127.0.0.1', '::1'):
|
||||
cherryhost = '0.0.0.0'
|
||||
try:
|
||||
info = socket.getaddrinfo(localhost, None)
|
||||
except:
|
||||
info = socket.getaddrinfo('127.0.0.1', None)
|
||||
localhost = '127.0.0.1'
|
||||
for item in info:
|
||||
ip = str(item[4][0])
|
||||
if ip.startswith('169.254.'):
|
||||
@@ -667,28 +672,27 @@ def get_webhost(cherryhost, cherryport, https_port):
|
||||
return cherryhost, cherryport, browserhost, https_port
|
||||
|
||||
|
||||
def attach_server(host, port, cert=None, key=None):
|
||||
def attach_server(host, port, cert=None, key=None, chain=None):
|
||||
""" Define and attach server, optionally HTTPS
|
||||
"""
|
||||
http_server = _cpwsgi_server.CPWSGIServer()
|
||||
http_server.bind_addr = (host, port)
|
||||
if cert and key:
|
||||
http_server.ssl_certificate = cert
|
||||
http_server.ssl_private_key = key
|
||||
adapter = _cpserver.ServerAdapter(cherrypy.engine, http_server, http_server.bind_addr)
|
||||
adapter.subscribe()
|
||||
if not (sabnzbd.cfg.no_ipv6() and '::1' in host):
|
||||
http_server = _cpwsgi_server.CPWSGIServer()
|
||||
http_server.bind_addr = (host, port)
|
||||
if cert and key:
|
||||
http_server.ssl_certificate = cert
|
||||
http_server.ssl_private_key = key
|
||||
http_server.ssl_certificate_chain = chain
|
||||
adapter = _cpserver.ServerAdapter(cherrypy.engine, http_server, http_server.bind_addr)
|
||||
adapter.subscribe()
|
||||
|
||||
|
||||
def is_sabnzbd_running(url):
|
||||
def is_sabnzbd_running(url, timeout=None):
|
||||
""" Return True when there's already a SABnzbd instance running.
|
||||
"""
|
||||
try:
|
||||
url = '%s&mode=version' % (url)
|
||||
ver = sabnzbd.newsunpack.get_from_url(url)
|
||||
if ver and ver.strip(' \n\r\t') == sabnzbd.__version__:
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
ver = sabnzbd.newsunpack.get_from_url(url, timeout=timeout)
|
||||
return bool(ver and re.search(r'\d+\.\d+\.', ver))
|
||||
except:
|
||||
return False
|
||||
|
||||
@@ -708,7 +712,7 @@ def find_free_port(host, currentport):
|
||||
|
||||
|
||||
def check_for_sabnzbd(url, upload_nzbs, allow_browser=True):
|
||||
""" Check for a running instance of sabnzbd(same version) on this port
|
||||
""" Check for a running instance of sabnzbd on this port
|
||||
allow_browser==True|None will launch the browser, False will not.
|
||||
"""
|
||||
if allow_browser is None:
|
||||
@@ -773,7 +777,7 @@ def evaluate_inipath(path):
|
||||
inipath = os.path.join(path, DEF_INI_FILE)
|
||||
if os.path.isdir(path):
|
||||
return inipath
|
||||
elif os.path.isfile(path):
|
||||
elif os.path.isfile(path) or os.path.isfile(path + '.bak'):
|
||||
return path
|
||||
else:
|
||||
dirpart, name = os.path.split(path)
|
||||
@@ -836,7 +840,7 @@ def commandline_handler(frozen=True):
|
||||
try:
|
||||
opts, args = getopt.getopt(info, "phdvncw:l:s:f:t:b:2:",
|
||||
['pause', 'help', 'daemon', 'nobrowser', 'clean', 'logging=',
|
||||
'weblogging=', 'server=', 'templates',
|
||||
'weblogging=', 'server=', 'templates', 'no_ipv6',
|
||||
'template2', 'browser=', 'config-file=', 'force',
|
||||
'version', 'https=', 'autorestarted', 'repair', 'repair-all',
|
||||
'log-all', 'no-login', 'pid=', 'new', 'sessions', 'console',
|
||||
@@ -914,6 +918,7 @@ def main():
|
||||
new_instance = False
|
||||
force_sessions = False
|
||||
osx_console = False
|
||||
no_ipv6 = False
|
||||
|
||||
service, sab_opts, serv_opts, upload_nzbs = commandline_handler()
|
||||
|
||||
@@ -1000,6 +1005,8 @@ def main():
|
||||
elif opt in ('--console',):
|
||||
re_argv.append(opt)
|
||||
osx_console = True
|
||||
elif opt in ('--no_ipv6',):
|
||||
no_ipv6 = True
|
||||
|
||||
sabnzbd.MY_FULLNAME = os.path.normpath(os.path.abspath(sabnzbd.MY_FULLNAME))
|
||||
sabnzbd.MY_NAME = os.path.basename(sabnzbd.MY_FULLNAME)
|
||||
@@ -1053,7 +1060,7 @@ def main():
|
||||
GetProfileInfo(vista_plus)
|
||||
# Find out where INI file is
|
||||
inifile = os.path.abspath(sabnzbd.DIR_PROG + '/' + DEF_INI_FILE)
|
||||
if not os.path.exists(inifile):
|
||||
if not os.path.exists(inifile) and not os.path.exists(inifile + '.bak'):
|
||||
inifile = os.path.abspath(sabnzbd.DIR_LCLDATA + '/' + DEF_INI_FILE)
|
||||
if sabnzbd.DARWIN:
|
||||
copy_old_files(sabnzbd.DIR_LCLDATA)
|
||||
@@ -1065,7 +1072,7 @@ def main():
|
||||
# All system data dirs are relative to the place we found the INI file
|
||||
sabnzbd.DIR_LCLDATA = os.path.dirname(inifile)
|
||||
|
||||
if not os.path.exists(inifile) and not os.path.exists(sabnzbd.DIR_LCLDATA):
|
||||
if not os.path.exists(inifile) and not os.path.exists(inifile + '.bak') and not os.path.exists(sabnzbd.DIR_LCLDATA):
|
||||
try:
|
||||
os.makedirs(sabnzbd.DIR_LCLDATA)
|
||||
except IOError:
|
||||
@@ -1082,6 +1089,9 @@ def main():
|
||||
# Set root folders for HTTPS server file paths
|
||||
sabnzbd.cfg.set_root_folders2()
|
||||
|
||||
if no_ipv6:
|
||||
sabnzbd.cfg.no_ipv6.set(True)
|
||||
|
||||
# Determine web host address
|
||||
cherryhost, cherryport, browserhost, https_port = get_webhost(cherryhost, cherryport, https_port)
|
||||
enable_https = sabnzbd.cfg.enable_https()
|
||||
@@ -1200,8 +1210,6 @@ def main():
|
||||
sabnzbd.cfg.log_backups())
|
||||
|
||||
format = '%(asctime)s::%(levelname)s::[%(module)s:%(lineno)d] %(message)s'
|
||||
if sabnzbd.WIN32:
|
||||
format += '\r'
|
||||
rollover_log.setFormatter(logging.Formatter(format))
|
||||
rollover_log.addFilter(FilterCP3())
|
||||
sabnzbd.LOGHANDLER = rollover_log
|
||||
@@ -1341,6 +1349,10 @@ def main():
|
||||
|
||||
https_cert = sabnzbd.cfg.https_cert.get_path()
|
||||
https_key = sabnzbd.cfg.https_key.get_path()
|
||||
https_chain = sabnzbd.cfg.https_chain.get_path()
|
||||
if not (sabnzbd.cfg.https_chain() and os.path.exists(https_chain)):
|
||||
https_chain = None
|
||||
|
||||
if enable_https:
|
||||
# If either the HTTPS certificate or key do not exist, make some self-signed ones.
|
||||
if not (https_cert and os.path.exists(https_cert)) or not (https_key and os.path.exists(https_key)):
|
||||
@@ -1359,8 +1371,8 @@ def main():
|
||||
hosts[1] = '::1'
|
||||
|
||||
# The Windows binary requires numeric localhost as primary address
|
||||
if multilocal and cherryhost == 'localhost' and hosts[1] == '127.0.0.1':
|
||||
cherryhost = '::1'
|
||||
if multilocal and cherryhost == 'localhost':
|
||||
cherryhost = hosts[0]
|
||||
|
||||
if enable_https:
|
||||
if https_port:
|
||||
@@ -1370,14 +1382,15 @@ def main():
|
||||
# Extra HTTP port for secondary localhost
|
||||
attach_server(hosts[1], cherryport)
|
||||
# Extra HTTPS port for secondary localhost
|
||||
attach_server(hosts[1], https_port, https_cert, https_key)
|
||||
attach_server(hosts[1], https_port, https_cert, https_key, https_chain)
|
||||
cherryport = https_port
|
||||
elif multilocal:
|
||||
# Extra HTTPS port for secondary localhost
|
||||
attach_server(hosts[1], cherryport, https_cert, https_key)
|
||||
|
||||
cherrypy.config.update({'server.ssl_certificate' : https_cert,
|
||||
'server.ssl_private_key' : https_key })
|
||||
'server.ssl_private_key' : https_key,
|
||||
'server.ssl_certificate_chain' : https_chain})
|
||||
elif multilocal:
|
||||
# Extra HTTP port for secondary localhost
|
||||
attach_server(hosts[1], cherryport)
|
||||
@@ -1395,6 +1408,17 @@ def main():
|
||||
else:
|
||||
sessions = None
|
||||
|
||||
mime_gzip = ('text/html',
|
||||
'text/plain',
|
||||
'text/css',
|
||||
'text/xml',
|
||||
'text/javascript',
|
||||
'application/javascript',
|
||||
'text/x-javascript',
|
||||
'application/x-javascript',
|
||||
'text/x-json',
|
||||
'application/json'
|
||||
)
|
||||
cherrypy.config.update({'server.environment': 'production',
|
||||
'server.socket_host': cherryhost,
|
||||
'server.socket_port': cherryport,
|
||||
@@ -1404,7 +1428,7 @@ def main():
|
||||
'engine.reexec_retry' : 100,
|
||||
'tools.encode.on' : True,
|
||||
'tools.gzip.on' : True,
|
||||
'tools.gzip.mime_types' : ['text/html', 'text/plain', 'text/javascript', 'text/css', 'application/x-javascript'],
|
||||
'tools.gzip.mime_types' : mime_gzip,
|
||||
'tools.sessions.on' : bool(sessions),
|
||||
'tools.sessions.storage_type' : 'file',
|
||||
'tools.sessions.storage_path' : sessions,
|
||||
@@ -1495,8 +1519,8 @@ def main():
|
||||
if sabnzbd.FOUNDATION:
|
||||
import sabnzbd.osxmenu
|
||||
sabnzbd.osxmenu.notify("SAB_Launched", None)
|
||||
growler.send_notification('SABnzbd %s' % (sabnzbd.__version__),
|
||||
"http://%s:%s/sabnzbd" % (browserhost, cherryport), 'startup')
|
||||
growler.send_notification('SABnzbd%s' % growler.hostname(),
|
||||
T('SABnzbd %s started') % sabnzbd.__version__, 'startup')
|
||||
# Now's the time to check for a new version
|
||||
check_latest_version()
|
||||
autorestarted = False
|
||||
@@ -1539,7 +1563,7 @@ def main():
|
||||
add_local(f)
|
||||
|
||||
# Have to keep this running, otherwise logging will terminate
|
||||
timer = 0
|
||||
timer = timer5 = 0
|
||||
while not sabnzbd.SABSTOP:
|
||||
if sabnzbd.WIN_SERVICE:
|
||||
rc = win32event.WaitForMultipleObjects((sabnzbd.WIN_SERVICE.hWaitStop,
|
||||
@@ -1565,7 +1589,7 @@ def main():
|
||||
### 30 sec polling tasks
|
||||
if timer > 9:
|
||||
timer = 0
|
||||
# Keep Windows awake (if needed)
|
||||
# Keep OS awake (if needed)
|
||||
sabnzbd.keep_awake()
|
||||
# Restart scheduler (if needed)
|
||||
scheduler.restart()
|
||||
@@ -1579,6 +1603,15 @@ def main():
|
||||
if sabnzbd.WIN_SERVICE and mail:
|
||||
mail.send('active')
|
||||
|
||||
if timer5 > 9:
|
||||
### 5 minute polling tasks
|
||||
timer5 = 0
|
||||
if sabnzbd.cfg.web_watchdog() and not is_sabnzbd_running('%s/api?tickleme=1' % sabnzbd.BROWSER_URL, 120):
|
||||
autorestarted = True
|
||||
cherrypy.engine.execv = True
|
||||
else:
|
||||
timer5 += 1
|
||||
|
||||
else:
|
||||
timer += 1
|
||||
|
||||
|
||||
@@ -658,7 +658,10 @@ class Request(object):
|
||||
# Handle cookies differently because on Konqueror, multiple
|
||||
# cookies come on different lines with the same key
|
||||
if name == 'Cookie':
|
||||
self.cookie.load(value)
|
||||
try:
|
||||
self.cookie.load(value)
|
||||
except:
|
||||
pass
|
||||
|
||||
if not dict.__contains__(headers, 'Host'):
|
||||
# All Internet-based HTTP/1.1 servers MUST respond with a 400
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import logging
|
||||
import cherrypy
|
||||
from cherrypy.lib import httpauth
|
||||
|
||||
@@ -9,10 +10,10 @@ def check_auth(users, encrypt=None, realm=None):
|
||||
ah = httpauth.parseAuthorization(cherrypy.request.headers['authorization'])
|
||||
if ah is None:
|
||||
raise cherrypy.HTTPError(400, 'Bad Request')
|
||||
|
||||
|
||||
if not encrypt:
|
||||
encrypt = httpauth.DIGEST_AUTH_ENCODERS[httpauth.MD5]
|
||||
|
||||
|
||||
if callable(users):
|
||||
try:
|
||||
# backward compatibility
|
||||
@@ -20,7 +21,7 @@ def check_auth(users, encrypt=None, realm=None):
|
||||
|
||||
if not isinstance(users, dict):
|
||||
raise ValueError, "Authentication users must be a dictionary"
|
||||
|
||||
|
||||
# fetch the user password
|
||||
password = users.get(ah["username"], None)
|
||||
except TypeError:
|
||||
@@ -29,23 +30,26 @@ def check_auth(users, encrypt=None, realm=None):
|
||||
else:
|
||||
if not isinstance(users, dict):
|
||||
raise ValueError, "Authentication users must be a dictionary"
|
||||
|
||||
|
||||
# fetch the user password
|
||||
password = users.get(ah["username"], None)
|
||||
|
||||
|
||||
# validate the authorization by re-computing it here
|
||||
# and compare it with what the user-agent provided
|
||||
if httpauth.checkResponse(ah, password, method=cherrypy.request.method,
|
||||
encrypt=encrypt, realm=realm):
|
||||
cherrypy.request.login = ah["username"]
|
||||
return True
|
||||
|
||||
|
||||
if ah.get('username') or ah.get('password'):
|
||||
logging.info('Attempt to login with wrong credentials from %s',
|
||||
cherrypy.request.headers['Remote-Addr'])
|
||||
cherrypy.request.login = False
|
||||
return False
|
||||
|
||||
def basic_auth(realm, users, encrypt=None):
|
||||
"""If auth fails, raise 401 with a basic authentication header.
|
||||
|
||||
|
||||
realm: a string containing the authentication realm.
|
||||
users: a dict of the form: {username: password} or a callable returning a dict.
|
||||
encrypt: callable used to encrypt the password returned from the user-agent.
|
||||
@@ -53,23 +57,23 @@ def basic_auth(realm, users, encrypt=None):
|
||||
"""
|
||||
if check_auth(users, encrypt):
|
||||
return
|
||||
|
||||
|
||||
# inform the user-agent this path is protected
|
||||
cherrypy.response.headers['www-authenticate'] = httpauth.basicAuth(realm)
|
||||
|
||||
raise cherrypy.HTTPError(401, "You are not authorized to access that resource")
|
||||
|
||||
raise cherrypy.HTTPError(401, "You are not authorized to access that resource")
|
||||
|
||||
def digest_auth(realm, users):
|
||||
"""If auth fails, raise 401 with a digest authentication header.
|
||||
|
||||
|
||||
realm: a string containing the authentication realm.
|
||||
users: a dict of the form: {username: password} or a callable returning a dict.
|
||||
"""
|
||||
if check_auth(users, realm=realm):
|
||||
return
|
||||
|
||||
|
||||
# inform the user-agent this path is protected
|
||||
cherrypy.response.headers['www-authenticate'] = httpauth.digestAuth(realm)
|
||||
|
||||
raise cherrypy.HTTPError(401, "You are not authorized to access that resource")
|
||||
|
||||
|
||||
raise cherrypy.HTTPError(401, "You are not authorized to access that resource")
|
||||
|
||||
|
||||
594
gntp/__init__.py
@@ -1,332 +1,402 @@
|
||||
import re
|
||||
import hashlib
|
||||
import time
|
||||
import platform
|
||||
import StringIO
|
||||
|
||||
__version__ = '0.8'
|
||||
|
||||
#GNTP/<version> <messagetype> <encryptionAlgorithmID>[:<ivValue>][ <keyHashAlgorithmID>:<keyHash>.<salt>]
|
||||
GNTP_INFO_LINE = re.compile(
|
||||
'GNTP/(?P<version>\d+\.\d+) (?P<messagetype>REGISTER|NOTIFY|SUBSCRIBE|\-OK|\-ERROR)' +
|
||||
' (?P<encryptionAlgorithmID>[A-Z0-9]+(:(?P<ivValue>[A-F0-9]+))?) ?' +
|
||||
'((?P<keyHashAlgorithmID>[A-Z0-9]+):(?P<keyHash>[A-F0-9]+).(?P<salt>[A-F0-9]+))?\r\n',
|
||||
re.IGNORECASE
|
||||
)
|
||||
|
||||
GNTP_INFO_LINE_SHORT = re.compile(
|
||||
'GNTP/(?P<version>\d+\.\d+) (?P<messagetype>REGISTER|NOTIFY|SUBSCRIBE|\-OK|\-ERROR)',
|
||||
re.IGNORECASE
|
||||
)
|
||||
|
||||
GNTP_HEADER = re.compile('([\w-]+):(.+)')
|
||||
|
||||
GNTP_EOL = '\r\n'
|
||||
|
||||
__version__ = '0.4'
|
||||
|
||||
class BaseError(Exception):
|
||||
pass
|
||||
def gntp_error(self):
|
||||
error = GNTPError(self.errorcode, self.errordesc)
|
||||
return error.encode()
|
||||
|
||||
|
||||
class ParseError(BaseError):
|
||||
def gntp_error(self):
|
||||
error = GNTPError(errorcode=500,errordesc='Error parsing the message')
|
||||
return error.encode()
|
||||
errorcode = 500
|
||||
errordesc = 'Error parsing the message'
|
||||
|
||||
|
||||
class AuthError(BaseError):
|
||||
def gntp_error(self):
|
||||
error = GNTPError(errorcode=400,errordesc='Error with authorization')
|
||||
return error.encode()
|
||||
errorcode = 400
|
||||
errordesc = 'Error with authorization'
|
||||
|
||||
|
||||
class UnsupportedError(BaseError):
|
||||
def gntp_error(self):
|
||||
error = GNTPError(errorcode=500,errordesc='Currently unsupported by gntp.py')
|
||||
return error.encode()
|
||||
errorcode = 500
|
||||
errordesc = 'Currently unsupported by gntp.py'
|
||||
|
||||
|
||||
class _GNTPBuffer(StringIO.StringIO):
|
||||
"""GNTP Buffer class"""
|
||||
def writefmt(self, message="", *args):
|
||||
"""Shortcut function for writing GNTP Headers"""
|
||||
self.write((message % args).encode('utf8', 'replace'))
|
||||
self.write(GNTP_EOL)
|
||||
|
||||
|
||||
class _GNTPBase(object):
|
||||
info = {
|
||||
'version':'1.0',
|
||||
'messagetype':None,
|
||||
'encryptionAlgorithmID':None
|
||||
}
|
||||
_requiredHeaders = []
|
||||
headers = {}
|
||||
resources = {}
|
||||
def add_origin_info(self):
|
||||
self.add_header('Origin-Machine-Name',platform.node())
|
||||
self.add_header('Origin-Software-Name','gntp.py')
|
||||
self.add_header('Origin-Software-Version',__version__)
|
||||
self.add_header('Origin-Platform-Name',platform.system())
|
||||
self.add_header('Origin-Platform-Version',platform.platform())
|
||||
"""Base initilization
|
||||
|
||||
:param string messagetype: GNTP Message type
|
||||
:param string version: GNTP Protocol version
|
||||
:param string encription: Encryption protocol
|
||||
"""
|
||||
def __init__(self, messagetype=None, version='1.0', encryption=None):
|
||||
self.info = {
|
||||
'version': version,
|
||||
'messagetype': messagetype,
|
||||
'encryptionAlgorithmID': encryption
|
||||
}
|
||||
self.headers = {}
|
||||
self.resources = {}
|
||||
|
||||
def __str__(self):
|
||||
return self.encode()
|
||||
def _parse_info(self,data):
|
||||
'''
|
||||
Parse the first line of a GNTP message to get security and other info values
|
||||
@param data: GNTP Message
|
||||
@return: GNTP Message information in a dictionary
|
||||
'''
|
||||
#GNTP/<version> <messagetype> <encryptionAlgorithmID>[:<ivValue>][ <keyHashAlgorithmID>:<keyHash>.<salt>]
|
||||
match = re.match('GNTP/(?P<version>\d+\.\d+) (?P<messagetype>REGISTER|NOTIFY|SUBSCRIBE|\-OK|\-ERROR)'+
|
||||
' (?P<encryptionAlgorithmID>[A-Z0-9]+(:(?P<ivValue>[A-F0-9]+))?) ?'+
|
||||
'((?P<keyHashAlgorithmID>[A-Z0-9]+):(?P<keyHash>[A-F0-9]+).(?P<salt>[A-F0-9]+))?\r\n', data,re.IGNORECASE)
|
||||
|
||||
|
||||
def _parse_info(self, data):
|
||||
"""Parse the first line of a GNTP message to get security and other info values
|
||||
|
||||
:param string data: GNTP Message
|
||||
:return dict: Parsed GNTP Info line
|
||||
"""
|
||||
|
||||
match = GNTP_INFO_LINE.match(data)
|
||||
|
||||
if not match:
|
||||
raise ParseError('ERROR_PARSING_INFO_LINE')
|
||||
|
||||
|
||||
info = match.groupdict()
|
||||
if info['encryptionAlgorithmID'] == 'NONE':
|
||||
info['encryptionAlgorithmID'] = None
|
||||
|
||||
|
||||
return info
|
||||
def set_password(self,password,encryptAlgo='MD5'):
|
||||
'''
|
||||
Set a password for a GNTP Message
|
||||
@param password: Null to clear password
|
||||
@param encryptAlgo: Supports MD5,SHA1,SHA256,SHA512
|
||||
@todo: Support other hash functions
|
||||
'''
|
||||
|
||||
def set_password(self, password, encryptAlgo='MD5'):
|
||||
"""Set a password for a GNTP Message
|
||||
|
||||
:param string password: Null to clear password
|
||||
:param string encryptAlgo: Supports MD5, SHA1, SHA256, SHA512
|
||||
"""
|
||||
hash = {
|
||||
'MD5': hashlib.md5,
|
||||
'SHA1': hashlib.sha1,
|
||||
'SHA256': hashlib.sha256,
|
||||
'SHA512': hashlib.sha512,
|
||||
}
|
||||
|
||||
|
||||
self.password = password
|
||||
self.encryptAlgo = encryptAlgo.upper()
|
||||
if not password:
|
||||
self.info['encryptionAlgorithmID'] = None
|
||||
self.info['keyHashAlgorithm'] = None;
|
||||
self.info['keyHashAlgorithm'] = None
|
||||
return
|
||||
if not self.encryptAlgo in hash.keys():
|
||||
raise UnsupportedError('INVALID HASH "%s"'%self.encryptAlgo)
|
||||
|
||||
raise UnsupportedError('INVALID HASH "%s"' % self.encryptAlgo)
|
||||
|
||||
hashfunction = hash.get(self.encryptAlgo)
|
||||
|
||||
|
||||
password = password.encode('utf8')
|
||||
seed = time.ctime()
|
||||
salt = hashfunction(seed).hexdigest()
|
||||
saltHash = hashfunction(seed).digest()
|
||||
keyBasis = password+saltHash
|
||||
keyBasis = password + saltHash
|
||||
key = hashfunction(keyBasis).digest()
|
||||
keyHash = hashfunction(key).hexdigest()
|
||||
|
||||
|
||||
self.info['keyHashAlgorithmID'] = self.encryptAlgo
|
||||
self.info['keyHash'] = keyHash.upper()
|
||||
self.info['salt'] = salt.upper()
|
||||
def _decode_hex(self,value):
|
||||
'''
|
||||
Helper function to decode hex string to `proper` hex string
|
||||
@param value: Value to decode
|
||||
@return: Hex string
|
||||
'''
|
||||
|
||||
def _decode_hex(self, value):
|
||||
"""Helper function to decode hex string to `proper` hex string
|
||||
|
||||
:param string value: Human readable hex string
|
||||
:return string: Hex string
|
||||
"""
|
||||
result = ''
|
||||
for i in range(0,len(value),2):
|
||||
tmp = int(value[i:i+2],16)
|
||||
for i in range(0, len(value), 2):
|
||||
tmp = int(value[i:i + 2], 16)
|
||||
result += chr(tmp)
|
||||
return result
|
||||
def _decode_binary(self,rawIdentifier,identifier):
|
||||
|
||||
def _decode_binary(self, rawIdentifier, identifier):
|
||||
rawIdentifier += '\r\n\r\n'
|
||||
dataLength = int(identifier['Length'])
|
||||
pointerStart = self.raw.find(rawIdentifier)+len(rawIdentifier)
|
||||
pointerStart = self.raw.find(rawIdentifier) + len(rawIdentifier)
|
||||
pointerEnd = pointerStart + dataLength
|
||||
data = self.raw[pointerStart:pointerEnd]
|
||||
if not len(data) == dataLength:
|
||||
raise ParseError('INVALID_DATA_LENGTH Expected: %s Recieved %s'%(dataLength,len(data)))
|
||||
raise ParseError('INVALID_DATA_LENGTH Expected: %s Recieved %s' % (dataLength, len(data)))
|
||||
return data
|
||||
def _validate_password(self,password):
|
||||
'''
|
||||
Validate GNTP Message against stored password
|
||||
'''
|
||||
|
||||
def _validate_password(self, password):
|
||||
"""Validate GNTP Message against stored password"""
|
||||
self.password = password
|
||||
if password == None: raise Exception()
|
||||
keyHash = self.info.get('keyHash',None)
|
||||
if password == None:
|
||||
raise AuthError('Missing password')
|
||||
keyHash = self.info.get('keyHash', None)
|
||||
if keyHash is None and self.password is None:
|
||||
return True
|
||||
if keyHash is None:
|
||||
raise AuthError('Invalid keyHash')
|
||||
if self.password is None:
|
||||
raise AuthError('Missing password')
|
||||
|
||||
|
||||
password = self.password.encode('utf8')
|
||||
saltHash = self._decode_hex(self.info['salt'])
|
||||
|
||||
keyBasis = password+saltHash
|
||||
|
||||
keyBasis = password + saltHash
|
||||
key = hashlib.md5(keyBasis).digest()
|
||||
keyHash = hashlib.md5(key).hexdigest()
|
||||
|
||||
|
||||
if not keyHash.upper() == self.info['keyHash'].upper():
|
||||
raise AuthError('Invalid Hash')
|
||||
return True
|
||||
|
||||
def validate(self):
|
||||
'''
|
||||
Verify required headers
|
||||
'''
|
||||
"""Verify required headers"""
|
||||
for header in self._requiredHeaders:
|
||||
if not self.headers.get(header,False):
|
||||
raise ParseError('Missing Notification Header: '+header)
|
||||
|
||||
if not self.headers.get(header, False):
|
||||
raise ParseError('Missing Notification Header: ' + header)
|
||||
|
||||
def _format_info(self):
|
||||
'''
|
||||
Generate info line for GNTP Message
|
||||
@return: Info line string
|
||||
'''
|
||||
info = u'GNTP/%s %s'%(
|
||||
"""Generate info line for GNTP Message
|
||||
|
||||
:return string:
|
||||
"""
|
||||
info = u'GNTP/%s %s' % (
|
||||
self.info.get('version'),
|
||||
self.info.get('messagetype'),
|
||||
)
|
||||
if self.info.get('encryptionAlgorithmID',None):
|
||||
info += ' %s:%s'%(
|
||||
if self.info.get('encryptionAlgorithmID', None):
|
||||
info += ' %s:%s' % (
|
||||
self.info.get('encryptionAlgorithmID'),
|
||||
self.info.get('ivValue'),
|
||||
)
|
||||
else:
|
||||
info+=' NONE'
|
||||
|
||||
if self.info.get('keyHashAlgorithmID',None):
|
||||
info += ' %s:%s.%s'%(
|
||||
info += ' NONE'
|
||||
|
||||
if self.info.get('keyHashAlgorithmID', None):
|
||||
info += ' %s:%s.%s' % (
|
||||
self.info.get('keyHashAlgorithmID'),
|
||||
self.info.get('keyHash'),
|
||||
self.info.get('salt')
|
||||
)
|
||||
|
||||
return info
|
||||
def _parse_dict(self,data):
|
||||
'''
|
||||
Helper function to parse blocks of GNTP headers into a dictionary
|
||||
@param data:
|
||||
@return: Dictionary of headers
|
||||
'''
|
||||
)
|
||||
|
||||
return info
|
||||
|
||||
def _parse_dict(self, data):
|
||||
"""Helper function to parse blocks of GNTP headers into a dictionary
|
||||
|
||||
:param string data:
|
||||
:return dict:
|
||||
"""
|
||||
dict = {}
|
||||
for line in data.split('\r\n'):
|
||||
match = re.match('([\w-]+):(.+)', line)
|
||||
if not match: continue
|
||||
|
||||
key = match.group(1).strip()
|
||||
val = match.group(2).strip()
|
||||
match = GNTP_HEADER.match(line)
|
||||
if not match:
|
||||
continue
|
||||
|
||||
key = unicode(match.group(1).strip(), 'utf8', 'replace')
|
||||
val = unicode(match.group(2).strip(), 'utf8', 'replace')
|
||||
dict[key] = val
|
||||
return dict
|
||||
def add_header(self,key,value):
|
||||
|
||||
def add_header(self, key, value):
|
||||
if isinstance(value, unicode):
|
||||
self.headers[key] = value
|
||||
else:
|
||||
self.headers[key] = unicode('%s'%value,'utf8','replace')
|
||||
def decode(self,data,password=None):
|
||||
'''
|
||||
Decode GNTP Message
|
||||
@param data:
|
||||
'''
|
||||
self.headers[key] = unicode('%s' % value, 'utf8', 'replace')
|
||||
|
||||
def add_resource(self, data):
|
||||
"""Add binary resource
|
||||
|
||||
:param string data: Binary Data
|
||||
"""
|
||||
identifier = hashlib.md5(data).hexdigest()
|
||||
self.resources[identifier] = data
|
||||
return 'x-growl-resource://%s' % identifier
|
||||
|
||||
def decode(self, data, password=None):
|
||||
"""Decode GNTP Message
|
||||
|
||||
:param string data:
|
||||
"""
|
||||
self.password = password
|
||||
self.raw = data
|
||||
parts = self.raw.split('\r\n\r\n')
|
||||
self.info = self._parse_info(data)
|
||||
self.headers = self._parse_dict(parts[0])
|
||||
|
||||
def encode(self):
|
||||
'''
|
||||
Encode a GNTP Message
|
||||
@return: GNTP Message ready to be sent
|
||||
'''
|
||||
self.validate()
|
||||
EOL = u'\r\n'
|
||||
|
||||
message = self._format_info() + EOL
|
||||
"""Encode a generic GNTP Message
|
||||
|
||||
:return string: GNTP Message ready to be sent
|
||||
"""
|
||||
|
||||
buffer = _GNTPBuffer()
|
||||
|
||||
buffer.writefmt(self._format_info())
|
||||
|
||||
#Headers
|
||||
for k,v in self.headers.iteritems():
|
||||
message += u'%s: %s%s'%(k,v,EOL)
|
||||
|
||||
message += EOL
|
||||
return message
|
||||
for k, v in self.headers.iteritems():
|
||||
buffer.writefmt('%s: %s', k, v)
|
||||
buffer.writefmt()
|
||||
|
||||
#Resources
|
||||
for resource, data in self.resources.iteritems():
|
||||
buffer.writefmt('Identifier: %s', resource)
|
||||
buffer.writefmt('Length: %d', len(data))
|
||||
buffer.writefmt()
|
||||
buffer.write(data)
|
||||
buffer.writefmt()
|
||||
buffer.writefmt()
|
||||
|
||||
return buffer.getvalue()
|
||||
|
||||
|
||||
class GNTPRegister(_GNTPBase):
|
||||
"""Represents a GNTP Registration Command"""
|
||||
notifications = []
|
||||
"""Represents a GNTP Registration Command
|
||||
|
||||
:param string data: (Optional) See decode()
|
||||
:param string password: (Optional) Password to use while encoding/decoding messages
|
||||
"""
|
||||
_requiredHeaders = [
|
||||
'Application-Name',
|
||||
'Notifications-Count'
|
||||
]
|
||||
_requiredNotificationHeaders = ['Notification-Name']
|
||||
def __init__(self,data=None,password=None):
|
||||
'''
|
||||
@param data: (Optional) See decode()
|
||||
@param password: (Optional) Password to use while encoding/decoding messages
|
||||
'''
|
||||
self.info['messagetype'] = 'REGISTER'
|
||||
|
||||
|
||||
def __init__(self, data=None, password=None):
|
||||
_GNTPBase.__init__(self, 'REGISTER')
|
||||
self.notifications = []
|
||||
|
||||
if data:
|
||||
self.decode(data,password)
|
||||
self.decode(data, password)
|
||||
else:
|
||||
self.set_password(password)
|
||||
self.add_header('Application-Name', 'pygntp')
|
||||
self.add_header('Notifications-Count', 0)
|
||||
self.add_origin_info()
|
||||
|
||||
def validate(self):
|
||||
'''
|
||||
Validate required headers and validate notification headers
|
||||
'''
|
||||
'''Validate required headers and validate notification headers'''
|
||||
for header in self._requiredHeaders:
|
||||
if not self.headers.get(header,False):
|
||||
raise ParseError('Missing Registration Header: '+header)
|
||||
if not self.headers.get(header, False):
|
||||
raise ParseError('Missing Registration Header: ' + header)
|
||||
for notice in self.notifications:
|
||||
for header in self._requiredNotificationHeaders:
|
||||
if not notice.get(header,False):
|
||||
raise ParseError('Missing Notification Header: '+header)
|
||||
def decode(self,data,password):
|
||||
'''
|
||||
Decode existing GNTP Registration message
|
||||
@param data: Message to decode.
|
||||
'''
|
||||
if not notice.get(header, False):
|
||||
raise ParseError('Missing Notification Header: ' + header)
|
||||
|
||||
def decode(self, data, password):
|
||||
"""Decode existing GNTP Registration message
|
||||
|
||||
:param string data: Message to decode
|
||||
"""
|
||||
self.raw = data
|
||||
parts = self.raw.split('\r\n\r\n')
|
||||
self.info = self._parse_info(data)
|
||||
self._validate_password(password)
|
||||
self.headers = self._parse_dict(parts[0])
|
||||
|
||||
for i,part in enumerate(parts):
|
||||
if i==0: continue #Skip Header
|
||||
if part.strip()=='': continue
|
||||
|
||||
for i, part in enumerate(parts):
|
||||
if i == 0:
|
||||
continue # Skip Header
|
||||
if part.strip() == '':
|
||||
continue
|
||||
notice = self._parse_dict(part)
|
||||
if notice.get('Notification-Name',False):
|
||||
if notice.get('Notification-Name', False):
|
||||
self.notifications.append(notice)
|
||||
elif notice.get('Identifier',False):
|
||||
notice['Data'] = self._decode_binary(part,notice)
|
||||
elif notice.get('Identifier', False):
|
||||
notice['Data'] = self._decode_binary(part, notice)
|
||||
#open('register.png','wblol').write(notice['Data'])
|
||||
self.resources[ notice.get('Identifier') ] = notice
|
||||
|
||||
def add_notification(self,name,enabled=True):
|
||||
'''
|
||||
Add new Notification to Registration message
|
||||
@param name: Notification Name
|
||||
@param enabled: Default Notification to Enabled
|
||||
'''
|
||||
self.resources[notice.get('Identifier')] = notice
|
||||
|
||||
def add_notification(self, name, enabled=True):
|
||||
"""Add new Notification to Registration message
|
||||
|
||||
:param string name: Notification Name
|
||||
:param boolean enabled: Enable this notification by default
|
||||
"""
|
||||
notice = {}
|
||||
notice['Notification-Name'] = u'%s'%name
|
||||
notice['Notification-Enabled'] = u'%s'%enabled
|
||||
|
||||
notice['Notification-Name'] = u'%s' % name
|
||||
notice['Notification-Enabled'] = u'%s' % enabled
|
||||
|
||||
self.notifications.append(notice)
|
||||
self.add_header('Notifications-Count', len(self.notifications))
|
||||
|
||||
def encode(self):
|
||||
'''
|
||||
Encode a GNTP Registration Message
|
||||
@return: GNTP Registration Message ready to be sent
|
||||
'''
|
||||
self.validate()
|
||||
EOL = u'\r\n'
|
||||
|
||||
message = self._format_info() + EOL
|
||||
"""Encode a GNTP Registration Message
|
||||
|
||||
:return string: Encoded GNTP Registration message
|
||||
"""
|
||||
|
||||
buffer = _GNTPBuffer()
|
||||
|
||||
buffer.writefmt(self._format_info())
|
||||
|
||||
#Headers
|
||||
for k,v in self.headers.iteritems():
|
||||
message += u'%s: %s%s'%(k,v,EOL)
|
||||
|
||||
for k, v in self.headers.iteritems():
|
||||
buffer.writefmt('%s: %s', k, v)
|
||||
buffer.writefmt()
|
||||
|
||||
#Notifications
|
||||
if len(self.notifications)>0:
|
||||
if len(self.notifications) > 0:
|
||||
for notice in self.notifications:
|
||||
message += EOL
|
||||
for k,v in notice.iteritems():
|
||||
message += u'%s: %s%s'%(k,v,EOL)
|
||||
|
||||
message += EOL
|
||||
return message
|
||||
for k, v in notice.iteritems():
|
||||
buffer.writefmt('%s: %s', k, v)
|
||||
buffer.writefmt()
|
||||
|
||||
#Resources
|
||||
for resource, data in self.resources.iteritems():
|
||||
buffer.writefmt('Identifier: %s', resource)
|
||||
buffer.writefmt('Length: %d', len(data))
|
||||
buffer.writefmt()
|
||||
buffer.write(data)
|
||||
buffer.writefmt()
|
||||
buffer.writefmt()
|
||||
|
||||
return buffer.getvalue()
|
||||
|
||||
|
||||
class GNTPNotice(_GNTPBase):
|
||||
"""Represents a GNTP Notification Command"""
|
||||
"""Represents a GNTP Notification Command
|
||||
|
||||
:param string data: (Optional) See decode()
|
||||
:param string app: (Optional) Set Application-Name
|
||||
:param string name: (Optional) Set Notification-Name
|
||||
:param string title: (Optional) Set Notification Title
|
||||
:param string password: (Optional) Password to use while encoding/decoding messages
|
||||
"""
|
||||
_requiredHeaders = [
|
||||
'Application-Name',
|
||||
'Notification-Name',
|
||||
'Notification-Title'
|
||||
]
|
||||
def __init__(self,data=None,app=None,name=None,title=None,password=None):
|
||||
'''
|
||||
|
||||
@param data: (Optional) See decode()
|
||||
@param app: (Optional) Set Application-Name
|
||||
@param name: (Optional) Set Notification-Name
|
||||
@param title: (Optional) Set Notification Title
|
||||
@param password: (Optional) Password to use while encoding/decoding messages
|
||||
'''
|
||||
self.info['messagetype'] = 'NOTIFY'
|
||||
|
||||
|
||||
def __init__(self, data=None, app=None, name=None, title=None, password=None):
|
||||
_GNTPBase.__init__(self, 'NOTIFY')
|
||||
|
||||
if data:
|
||||
self.decode(data,password)
|
||||
self.decode(data, password)
|
||||
else:
|
||||
self.set_password(password)
|
||||
if app:
|
||||
@@ -335,105 +405,103 @@ class GNTPNotice(_GNTPBase):
|
||||
self.add_header('Notification-Name', name)
|
||||
if title:
|
||||
self.add_header('Notification-Title', title)
|
||||
self.add_origin_info()
|
||||
def decode(self,data,password):
|
||||
'''
|
||||
Decode existing GNTP Notification message
|
||||
@param data: Message to decode.
|
||||
'''
|
||||
|
||||
def decode(self, data, password):
|
||||
"""Decode existing GNTP Notification message
|
||||
|
||||
:param string data: Message to decode.
|
||||
"""
|
||||
self.raw = data
|
||||
parts = self.raw.split('\r\n\r\n')
|
||||
self.info = self._parse_info(data)
|
||||
self._validate_password(password)
|
||||
self.headers = self._parse_dict(parts[0])
|
||||
|
||||
for i,part in enumerate(parts):
|
||||
if i==0: continue #Skip Header
|
||||
if part.strip()=='': continue
|
||||
|
||||
for i, part in enumerate(parts):
|
||||
if i == 0:
|
||||
continue # Skip Header
|
||||
if part.strip() == '':
|
||||
continue
|
||||
notice = self._parse_dict(part)
|
||||
if notice.get('Identifier',False):
|
||||
notice['Data'] = self._decode_binary(part,notice)
|
||||
if notice.get('Identifier', False):
|
||||
notice['Data'] = self._decode_binary(part, notice)
|
||||
#open('notice.png','wblol').write(notice['Data'])
|
||||
self.resources[ notice.get('Identifier') ] = notice
|
||||
def encode(self):
|
||||
'''
|
||||
Encode a GNTP Notification Message
|
||||
@return: GNTP Notification Message ready to be sent
|
||||
'''
|
||||
self.validate()
|
||||
EOL = u'\r\n'
|
||||
|
||||
message = self._format_info() + EOL
|
||||
#Headers
|
||||
for k,v in self.headers.iteritems():
|
||||
message += u'%s: %s%s'%(k,v,EOL)
|
||||
|
||||
message += EOL
|
||||
return message
|
||||
self.resources[notice.get('Identifier')] = notice
|
||||
|
||||
|
||||
class GNTPSubscribe(_GNTPBase):
|
||||
"""Represents a GNTP Subscribe Command"""
|
||||
def __init__(self,data=None,password=None):
|
||||
self.info['messagetype'] = 'SUBSCRIBE'
|
||||
self._requiredHeaders = [
|
||||
'Subscriber-ID',
|
||||
'Subscriber-Name',
|
||||
]
|
||||
"""Represents a GNTP Subscribe Command
|
||||
|
||||
:param string data: (Optional) See decode()
|
||||
:param string password: (Optional) Password to use while encoding/decoding messages
|
||||
"""
|
||||
_requiredHeaders = [
|
||||
'Subscriber-ID',
|
||||
'Subscriber-Name',
|
||||
]
|
||||
|
||||
def __init__(self, data=None, password=None):
|
||||
_GNTPBase.__init__(self, 'SUBSCRIBE')
|
||||
if data:
|
||||
self.decode(data,password)
|
||||
self.decode(data, password)
|
||||
else:
|
||||
self.set_password(password)
|
||||
self.add_origin_info()
|
||||
|
||||
|
||||
class GNTPOK(_GNTPBase):
|
||||
"""Represents a GNTP OK Response"""
|
||||
"""Represents a GNTP OK Response
|
||||
|
||||
:param string data: (Optional) See _GNTPResponse.decode()
|
||||
:param string action: (Optional) Set type of action the OK Response is for
|
||||
"""
|
||||
_requiredHeaders = ['Response-Action']
|
||||
def __init__(self,data=None,action=None):
|
||||
'''
|
||||
@param data: (Optional) See _GNTPResponse.decode()
|
||||
@param action: (Optional) Set type of action the OK Response is for
|
||||
'''
|
||||
self.info['messagetype'] = '-OK'
|
||||
|
||||
def __init__(self, data=None, action=None):
|
||||
_GNTPBase.__init__(self, '-OK')
|
||||
if data:
|
||||
self.decode(data)
|
||||
if action:
|
||||
self.add_header('Response-Action', action)
|
||||
self.add_origin_info()
|
||||
|
||||
|
||||
class GNTPError(_GNTPBase):
|
||||
_requiredHeaders = ['Error-Code','Error-Description']
|
||||
def __init__(self,data=None,errorcode=None,errordesc=None):
|
||||
'''
|
||||
@param data: (Optional) See _GNTPResponse.decode()
|
||||
@param errorcode: (Optional) Error code
|
||||
@param errordesc: (Optional) Error Description
|
||||
'''
|
||||
self.info['messagetype'] = '-ERROR'
|
||||
"""Represents a GNTP Error response
|
||||
|
||||
:param string data: (Optional) See _GNTPResponse.decode()
|
||||
:param string errorcode: (Optional) Error code
|
||||
:param string errordesc: (Optional) Error Description
|
||||
"""
|
||||
_requiredHeaders = ['Error-Code', 'Error-Description']
|
||||
|
||||
def __init__(self, data=None, errorcode=None, errordesc=None):
|
||||
_GNTPBase.__init__(self, '-ERROR')
|
||||
if data:
|
||||
self.decode(data)
|
||||
if errorcode:
|
||||
self.add_header('Error-Code', errorcode)
|
||||
self.add_header('Error-Description', errordesc)
|
||||
self.add_origin_info()
|
||||
def error(self):
|
||||
return self.headers['Error-Code'],self.headers['Error-Description']
|
||||
|
||||
def parse_gntp(data,password=None):
|
||||
'''
|
||||
Attempt to parse a message as a GNTP message
|
||||
@param data: Message to be parsed
|
||||
@param password: Optional password to be used to verify the message
|
||||
'''
|
||||
match = re.match('GNTP/(?P<version>\d+\.\d+) (?P<messagetype>REGISTER|NOTIFY|SUBSCRIBE|\-OK|\-ERROR)',data,re.IGNORECASE)
|
||||
def error(self):
|
||||
return (self.headers.get('Error-Code', None),
|
||||
self.headers.get('Error-Description', None))
|
||||
|
||||
|
||||
def parse_gntp(data, password=None):
|
||||
"""Attempt to parse a message as a GNTP message
|
||||
|
||||
:param string data: Message to be parsed
|
||||
:param string password: Optional password to be used to verify the message
|
||||
"""
|
||||
match = GNTP_INFO_LINE_SHORT.match(data)
|
||||
if not match:
|
||||
raise ParseError('INVALID_GNTP_INFO')
|
||||
info = match.groupdict()
|
||||
if info['messagetype'] == 'REGISTER':
|
||||
return GNTPRegister(data,password=password)
|
||||
return GNTPRegister(data, password=password)
|
||||
elif info['messagetype'] == 'NOTIFY':
|
||||
return GNTPNotice(data,password=password)
|
||||
return GNTPNotice(data, password=password)
|
||||
elif info['messagetype'] == 'SUBSCRIBE':
|
||||
return GNTPSubscribe(data,password=password)
|
||||
return GNTPSubscribe(data, password=password)
|
||||
elif info['messagetype'] == '-OK':
|
||||
return GNTPOK(data)
|
||||
elif info['messagetype'] == '-ERROR':
|
||||
|
||||
217
gntp/notifier.py
@@ -12,10 +12,55 @@ using GNTP
|
||||
import gntp
|
||||
import socket
|
||||
import logging
|
||||
import platform
|
||||
|
||||
__all__ = [
|
||||
'mini',
|
||||
'GrowlNotifier',
|
||||
]
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def mini(description, applicationName='PythonMini', noteType="Message",
|
||||
title="Mini Message", applicationIcon=None, hostname='localhost',
|
||||
password=None, port=23053, sticky=False, priority=None,
|
||||
callback=None, notificationIcon=None, identifier=None):
|
||||
"""Single notification function
|
||||
|
||||
Simple notification function in one line. Has only one required parameter
|
||||
and attempts to use reasonable defaults for everything else
|
||||
:param string description: Notification message
|
||||
|
||||
.. warning::
|
||||
For now, only URL callbacks are supported. In the future, the
|
||||
callback argument will also support a function
|
||||
"""
|
||||
growl = GrowlNotifier(
|
||||
applicationName=applicationName,
|
||||
notifications=[noteType],
|
||||
defaultNotifications=[noteType],
|
||||
applicationIcon=applicationIcon,
|
||||
hostname=hostname,
|
||||
password=password,
|
||||
port=port,
|
||||
)
|
||||
result = growl.register()
|
||||
if result is not True:
|
||||
return result
|
||||
|
||||
return growl.notify(
|
||||
noteType=noteType,
|
||||
title=title,
|
||||
description=description,
|
||||
icon=notificationIcon,
|
||||
sticky=sticky,
|
||||
priority=priority,
|
||||
callback=callback,
|
||||
identifier=identifier,
|
||||
)
|
||||
|
||||
|
||||
class GrowlNotifier(object):
|
||||
"""Helper class to simplfy sending Growl messages
|
||||
|
||||
@@ -27,55 +72,35 @@ class GrowlNotifier(object):
|
||||
:param string hostname: Remote host
|
||||
:param integer port: Remote port
|
||||
"""
|
||||
applicationName = 'Python GNTP'
|
||||
notifications = []
|
||||
defaultNotifications = []
|
||||
applicationIcon = None
|
||||
|
||||
passwordHash = 'MD5'
|
||||
socketTimeout = 3
|
||||
|
||||
#GNTP Specific
|
||||
password = None
|
||||
hostname = 'localhost'
|
||||
port = 23053
|
||||
def __init__(self, applicationName='Python GNTP', notifications=[],
|
||||
defaultNotifications=None, applicationIcon=None, hostname='localhost',
|
||||
password=None, port=23053):
|
||||
|
||||
def __init__(self, applicationName=None, notifications=None, defaultNotifications=None, applicationIcon=None, hostname=None, password=None, port=None):
|
||||
if applicationName:
|
||||
self.applicationName = applicationName
|
||||
assert self.applicationName, 'An application name is required.'
|
||||
|
||||
if notifications:
|
||||
self.notifications = list(notifications)
|
||||
assert self.notifications, 'A sequence of one or more notification names is required.'
|
||||
|
||||
if defaultNotifications is not None:
|
||||
self.applicationName = applicationName
|
||||
self.notifications = list(notifications)
|
||||
if defaultNotifications:
|
||||
self.defaultNotifications = list(defaultNotifications)
|
||||
elif not self.defaultNotifications:
|
||||
self.defaultNotifications = list(self.notifications)
|
||||
else:
|
||||
self.defaultNotifications = self.notifications
|
||||
self.applicationIcon = applicationIcon
|
||||
|
||||
if applicationIcon is not None:
|
||||
self.applicationIcon = self._checkIcon(applicationIcon)
|
||||
elif self.applicationIcon is not None:
|
||||
self.applicationIcon = self._checkIcon(self.applicationIcon)
|
||||
|
||||
#GNTP Specific
|
||||
if password:
|
||||
self.password = password
|
||||
|
||||
if hostname:
|
||||
self.hostname = hostname
|
||||
assert self.hostname, 'Requires valid hostname'
|
||||
|
||||
if port:
|
||||
self.port = int(port)
|
||||
assert isinstance(self.port, int), 'Requires valid port'
|
||||
self.password = password
|
||||
self.hostname = hostname
|
||||
self.port = int(port)
|
||||
|
||||
def _checkIcon(self, data):
|
||||
'''
|
||||
Check the icon to see if it's valid
|
||||
@param data:
|
||||
@todo Consider checking for a valid URL
|
||||
|
||||
If it's a simple URL icon, then we return True. If it's a data icon
|
||||
then we return False
|
||||
'''
|
||||
return data
|
||||
logger.debug('Checking icon')
|
||||
return data.startswith('http')
|
||||
|
||||
def register(self):
|
||||
"""Send GNTP Registration
|
||||
@@ -84,23 +109,26 @@ class GrowlNotifier(object):
|
||||
Before sending notifications to Growl, you need to have
|
||||
sent a registration message at least once
|
||||
"""
|
||||
logger.info('Sending registration to %s:%s', self.hostname, self.port)
|
||||
logger.debug('Sending registration to %s:%s', self.hostname, self.port)
|
||||
register = gntp.GNTPRegister()
|
||||
register.add_header('Application-Name', self.applicationName)
|
||||
for notification in self.notifications:
|
||||
enabled = notification in self.defaultNotifications
|
||||
register.add_notification(notification, enabled)
|
||||
if self.applicationIcon:
|
||||
register.add_header('Application-Icon', self.applicationIcon)
|
||||
if self._checkIcon(self.applicationIcon):
|
||||
register.add_header('Application-Icon', self.applicationIcon)
|
||||
else:
|
||||
id = register.add_resource(self.applicationIcon)
|
||||
register.add_header('Application-Icon', id)
|
||||
if self.password:
|
||||
register.set_password(self.password, self.passwordHash)
|
||||
response = self._send('register', register.encode())
|
||||
if isinstance(response, gntp.GNTPOK):
|
||||
return True
|
||||
logger.error('Invalid response %s', response.error())
|
||||
return response.error()
|
||||
self.add_origin_info(register)
|
||||
self.register_hook(register)
|
||||
return self._send('register', register)
|
||||
|
||||
def notify(self, noteType, title, description, icon=None, sticky=False, priority=None):
|
||||
def notify(self, noteType, title, description, icon=None, sticky=False,
|
||||
priority=None, callback=None, identifier=None):
|
||||
"""Send a GNTP notifications
|
||||
|
||||
.. warning::
|
||||
@@ -112,8 +140,13 @@ class GrowlNotifier(object):
|
||||
:param string icon: Icon URL path
|
||||
:param boolean sticky: Sticky notification
|
||||
:param integer priority: Message priority level from -2 to 2
|
||||
:param string callback: URL callback
|
||||
|
||||
.. warning::
|
||||
For now, only URL callbacks are supported. In the future, the
|
||||
callback argument will also support a function
|
||||
"""
|
||||
logger.info('Sending notification [%s] to %s:%s', noteType, self.hostname, self.port)
|
||||
logger.debug('Sending notification [%s] to %s:%s', noteType, self.hostname, self.port)
|
||||
assert noteType in self.notifications
|
||||
notice = gntp.GNTPNotice()
|
||||
notice.add_header('Application-Name', self.applicationName)
|
||||
@@ -126,14 +159,23 @@ class GrowlNotifier(object):
|
||||
if priority:
|
||||
notice.add_header('Notification-Priority', priority)
|
||||
if icon:
|
||||
notice.add_header('Notification-Icon', self._checkIcon(icon))
|
||||
if self._checkIcon(icon):
|
||||
notice.add_header('Notification-Icon', icon)
|
||||
else:
|
||||
id = notice.add_resource(icon)
|
||||
notice.add_header('Notification-Icon', id)
|
||||
|
||||
if description:
|
||||
notice.add_header('Notification-Text', description)
|
||||
response = self._send('notify', notice.encode())
|
||||
if isinstance(response, gntp.GNTPOK):
|
||||
return True
|
||||
logger.error('Invalid response %s', response.error())
|
||||
return response.error()
|
||||
if callback:
|
||||
notice.add_header('Notification-Callback-Target', callback)
|
||||
if identifier:
|
||||
notice.add_header('Notification-Coalescing-ID', identifier)
|
||||
|
||||
self.add_origin_info(notice)
|
||||
self.notify_hook(notice)
|
||||
|
||||
return self._send('notify', notice)
|
||||
|
||||
def subscribe(self, id, name, port):
|
||||
"""Send a Subscribe request to a remote machine"""
|
||||
@@ -143,30 +185,63 @@ class GrowlNotifier(object):
|
||||
sub.add_header('Subscriber-Port', port)
|
||||
if self.password:
|
||||
sub.set_password(self.password, self.passwordHash)
|
||||
response = self._send('subscribe', sub.encode())
|
||||
if isinstance(response, gntp.GNTPOK):
|
||||
return True
|
||||
logger.error('Invalid response %s', response.error())
|
||||
return response.error()
|
||||
|
||||
def _send(self, type, data):
|
||||
self.add_origin_info(sub)
|
||||
self.subscribe_hook(sub)
|
||||
|
||||
return self._send('subscribe', sub)
|
||||
|
||||
def add_origin_info(self, packet):
|
||||
"""Add optional Origin headers to message"""
|
||||
packet.add_header('Origin-Machine-Name', platform.node())
|
||||
packet.add_header('Origin-Software-Name', 'gntp.py')
|
||||
packet.add_header('Origin-Software-Version', gntp.__version__)
|
||||
packet.add_header('Origin-Platform-Name', platform.system())
|
||||
packet.add_header('Origin-Platform-Version', platform.platform())
|
||||
|
||||
def register_hook(self, packet):
|
||||
pass
|
||||
|
||||
def notify_hook(self, packet):
|
||||
pass
|
||||
|
||||
def subscribe_hook(self, packet):
|
||||
pass
|
||||
|
||||
def _send(self, messagetype, packet):
|
||||
"""Send the GNTP Packet"""
|
||||
#logger.debug('To : %s:%s <%s>\n%s', self.hostname, self.port, type, data)
|
||||
#Less verbose please
|
||||
logger.debug('To : %s:%s <%s>', self.hostname, self.port, type)
|
||||
|
||||
packet.validate()
|
||||
data = packet.encode()
|
||||
|
||||
#logger.debug('To : %s:%s <%s>\n%s', self.hostname, self.port, packet.__class__, data)
|
||||
#Less verbose
|
||||
logger.debug('To : %s:%s <%s>', self.hostname, self.port, packet.__class__)
|
||||
|
||||
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
|
||||
s.settimeout(self.socketTimeout)
|
||||
s.connect((self.hostname, self.port))
|
||||
s.send(data.encode('utf8', 'replace'))
|
||||
try:
|
||||
s.settimeout(10)
|
||||
except:
|
||||
pass
|
||||
response = gntp.parse_gntp(s.recv(1024))
|
||||
s.send(data)
|
||||
recv_data = s.recv(1024)
|
||||
while not recv_data.endswith("\r\n\r\n"):
|
||||
recv_data += s.recv(1024)
|
||||
response = gntp.parse_gntp(recv_data)
|
||||
s.close()
|
||||
|
||||
#logger.debug('From : %s:%s <%s>\n%s', self.hostname, self.port, response.__class__, response)
|
||||
#Less verbose please
|
||||
#Less verbose
|
||||
logger.debug('From : %s:%s <%s>', self.hostname, self.port, response.__class__)
|
||||
|
||||
return response
|
||||
if type(response) == gntp.GNTPOK:
|
||||
return True
|
||||
if response.error()[0] == '404' and 'disabled' in response.error()[1]:
|
||||
# Ignore message saying that user has disabled this class
|
||||
return True
|
||||
logger.error('Invalid response: %s', response.error())
|
||||
return response.error()
|
||||
|
||||
if __name__ == '__main__':
|
||||
# If we're running this module directly we're likely running it as a test
|
||||
# so extra debugging is useful
|
||||
logging.basicConfig(level=logging.DEBUG)
|
||||
mini('Testing mini notification')
|
||||
|
||||
@@ -6,59 +6,6 @@
|
||||
<!--#set global $submenu="newzbin"#-->
|
||||
<!--#include $webdir + "/inc_cmenu.tmpl"#-->
|
||||
|
||||
<h2>Newzbin</h2>
|
||||
$T('explain-newzbin')<br/><br/>
|
||||
<form action="saveNewzbin" method="post" autocomplete="off">
|
||||
<div class="EntryBlock">
|
||||
<fieldset class="EntryFieldSet">
|
||||
<legend>$T('accountInfo')</legend>
|
||||
<strong>$T('opt-username_newzbin'):</strong><br>
|
||||
$T('explain-username_newzbin')<br>
|
||||
<input type="text" name="username_newzbin" value="$username_newzbin">
|
||||
<br>
|
||||
<br>
|
||||
<strong>$T('opt-password_newzbin'):</strong><br>
|
||||
$T('explain-password_newzbin')<br>
|
||||
<input type="password" name="password_newzbin" value="$password_newzbin">
|
||||
</fieldset>
|
||||
</div>
|
||||
|
||||
<div class="EntryBlock">
|
||||
<fieldset class="EntryFieldSet">
|
||||
<legend>$T('newzbinBookmarks')</legend>
|
||||
<label><input type="checkbox" name="newzbin_bookmarks" value="1" <!--#if $newzbin_bookmarks > 0 then "checked=1" else ""#--> <strong>$T('opt-newzbin_bookmarks'):</strong></label><br>
|
||||
$T('explain-newzbin_bookmarks')<br>
|
||||
<a href="getBookmarks?session=$session">$T('link-getBookmarks')</a>
|
||||
<br>
|
||||
<!--#if $bookmarks_list#-->
|
||||
<a href="hideBookmarks?session=$session">$T('link-HideBM')</a>
|
||||
<!--#else#-->
|
||||
<a href="showBookmarks?session=$session">$T('link-ShowBM')</a>
|
||||
<!--#end if#-->
|
||||
<br/>
|
||||
<br/>
|
||||
<label><input type="checkbox" name="newzbin_unbookmark" value="1" <!--#if $newzbin_unbookmark > 0 then "checked=1" else ""#--> /> <strong>$T('opt-newzbin_unbookmark'):</strong></label><br>
|
||||
$T('explain-newzbin_unbookmark')<br>
|
||||
<br/>
|
||||
<strong>$T('opt-bookmark_rate'):</strong><br>
|
||||
$T('explain-bookmark_rate')<br>
|
||||
<input type="text" name="bookmark_rate" value="$bookmark_rate">
|
||||
</fieldset>
|
||||
</div>
|
||||
<!--#if $bookmarks_list#-->
|
||||
<fieldset class="EntryFieldSet">
|
||||
<legend>$T('processedBM')</legend>
|
||||
<!--#for $msgid in $bookmarks_list#-->
|
||||
<a href="https://$newzbin_url/browse/post/$msgid/" target="_blank">$msgid</a>
|
||||
<!--#end for#-->
|
||||
</fieldset>
|
||||
<!--#end if#-->
|
||||
<input type="hidden" name="session" value="$session">
|
||||
<p><input type="submit" value="$T('button-saveChanges')"></p>
|
||||
</form>
|
||||
|
||||
<hr/>
|
||||
|
||||
<h2>NzbMatrix</h2>
|
||||
$T('explain-nzbmatrix')<br/><br/>
|
||||
|
||||
|
||||
@@ -73,6 +73,7 @@
|
||||
<table>
|
||||
<tr>
|
||||
<th> </th>
|
||||
<th> </th>
|
||||
<th>$T('rss-order')</th>
|
||||
<th>$T('rss-type')</th>
|
||||
<th>$T('rss-filter')</th>
|
||||
@@ -86,6 +87,7 @@
|
||||
<form action="upd_rss_filter" method="get">
|
||||
<tr class="odd">
|
||||
<td></td>
|
||||
<td><input type="checkbox" name="enabled" value="1" checked="checked" /></td>
|
||||
<td></td>
|
||||
<td>
|
||||
<select name="filter_type">
|
||||
@@ -152,6 +154,10 @@
|
||||
</td>
|
||||
|
||||
<form action="upd_rss_filter" method="get">
|
||||
<td>
|
||||
<input type="checkbox" name="enabled" value="1" <!--#if $filter[6] == '1' then 'checked="checked"' else ""#--> />
|
||||
</td>
|
||||
|
||||
<td>
|
||||
<input type="text" size="3" name="new_index" value=$fnum>
|
||||
</td>
|
||||
@@ -208,6 +214,7 @@
|
||||
<input type="hidden" name="feed" value="$feed"/>
|
||||
<input type="hidden" name="session" value="$session">
|
||||
<input type="submit" value="$T('button-save')"/>
|
||||
<!--#if not $rss[$feed].filter_states[$fnum]#--> $T('Incorrect filter')<!--#end if#-->
|
||||
</td>
|
||||
</form>
|
||||
</tr>
|
||||
|
||||
@@ -31,16 +31,14 @@ $T('hour'):<br>
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
<br>$T('sch-frequency'): <br>
|
||||
<select name="dayofweek">
|
||||
<option value="*" selected>$T('daily')
|
||||
<option value="1">$T('monday')
|
||||
<option value="2">$T('tuesday')
|
||||
<option value="3">$T('wednesday')
|
||||
<option value="4">$T('thursday')
|
||||
<option value="5">$T('friday')
|
||||
<option value="6">$T('saturday')
|
||||
<option value="7">$T('sunday')
|
||||
</select>
|
||||
<input type="checkbox" name="daysofweek" value="1">$T('monday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="2">$T('tuesday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="3">$T('wednesday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="4">$T('thursday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="5">$T('friday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="6">$T('saturday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="7">$T('sunday')<br/>
|
||||
|
||||
<br>$T('sch-action'):<br>
|
||||
<select name="action">
|
||||
<!--#for $action in $actions#-->
|
||||
|
||||
@@ -47,11 +47,13 @@
|
||||
<a href="$cpath/notify/">$T('cmenu-notif')</a> |
|
||||
<!--#end if#-->
|
||||
|
||||
<!--#if 0#-->
|
||||
<!--#if $submenu=="indexers"#-->
|
||||
<a class="current" href="./">$T('cmenu-newzbin')</a> |
|
||||
<!--#else#-->
|
||||
<a href="$cpath/indexers/">$T('cmenu-newzbin')</a> |
|
||||
<!--#end if#-->
|
||||
<!--#end if#-->
|
||||
|
||||
<!--#if $submenu=="categories"#-->
|
||||
<a class="current" href="./">$T('cmenu-cat')</a> |
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN">
|
||||
<html>
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||
<title>$mbleft MB $T('queued') - SABnzbd $version</title>
|
||||
<link rel="stylesheet" type="text/css" href="$statpath/static/stylesheets/default.css"/>
|
||||
<link rel="stylesheet" type="text/css" href="$statpath/static/stylesheets/defaultcolors.css"/>
|
||||
|
||||
@@ -17,8 +17,7 @@
|
||||
<div class="EntryBlock">
|
||||
<form action="addID" method="get">
|
||||
<fieldset class="EntryFieldSet">
|
||||
<legend>$T('add')
|
||||
<!--#if $varExists('newzbinDetails')#--> $T('reportId') / <!--#end if#-->URL</legend>
|
||||
<legend>$T('add') URL</legend>
|
||||
<input type="text" name="id">
|
||||
<!--#if $cat_list#-->
|
||||
<select name="cat" >
|
||||
|
||||
54
interfaces/Config/README.txt
Normal file
@@ -0,0 +1,54 @@
|
||||
|
||||
uniConfig for SABnzbd 0.7.x
|
||||
zoggy@sabnzbd.org
|
||||
|
||||
|
||||
========================================================
|
||||
LIBRARIES USED
|
||||
|
||||
jQuery
|
||||
* Project repository: https://github.com/jquery/jquery
|
||||
* Dual licensed under the MIT and GPL licenses:
|
||||
* http://www.gnu.org/licenses/gpl.html
|
||||
* http://www.opensource.org/licenses/mit-license.php
|
||||
|
||||
jQuery UI
|
||||
* Project repository: https://github.com/jquery/jquery-ui
|
||||
* Dual licensed under the MIT and GPL licenses:
|
||||
* http://www.gnu.org/licenses/gpl.html
|
||||
* http://www.opensource.org/licenses/mit-license.php
|
||||
|
||||
jQuery Form Plugin
|
||||
* Project repository: https://github.com/malsup/form
|
||||
* Dual licensed under the MIT and GPL licenses:
|
||||
* http://www.gnu.org/licenses/gpl.html
|
||||
* http://www.opensource.org/licenses/mit-license.php
|
||||
|
||||
jQuery Tools (tabs)
|
||||
* Project repository: https://github.com/jquerytools/jquerytools
|
||||
|
||||
Formalize
|
||||
* Project repository: https://github.com/nathansmith/formalize
|
||||
* Dual licensed under the MIT and GPL licenses:
|
||||
* http://www.gnu.org/licenses/gpl.html
|
||||
* http://www.opensource.org/licenses/mit-license.php
|
||||
|
||||
normalize.css
|
||||
* Project repository: https://github.com/necolas/normalize.css
|
||||
* Licensed under public domain
|
||||
|
||||
qTip2
|
||||
* Project repository: https://github.com/craga89/qtip2
|
||||
* Dual licensed under the MIT and GPL licenses:
|
||||
* http://www.gnu.org/licenses/gpl.html
|
||||
* http://www.opensource.org/licenses/mit-license.php
|
||||
|
||||
|
||||
========================================================
|
||||
IMAGES USED
|
||||
|
||||
/images/loading-*.gif
|
||||
- source: http://www.AjaxLoad.info
|
||||
|
||||
/images/flags/*
|
||||
- source: http://www.famfamfam.com/lab/icons/flags/
|
||||
14
interfaces/Config/templates/_inc_footer_uc.tmpl
Normal file
@@ -0,0 +1,14 @@
|
||||
<!-- Content end -->
|
||||
</div>
|
||||
<script>
|
||||
function is_touch_device() {
|
||||
return !!('ontouchstart' in window) ? 1 : 0;
|
||||
}
|
||||
if (is_touch_device() === 1) {
|
||||
// touch device found
|
||||
\$('#content').css('overflow-y', 'inherit');
|
||||
\$('html').css('overflow-y', 'scroll');
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
156
interfaces/Config/templates/_inc_header_uc.tmpl
Normal file
@@ -0,0 +1,156 @@
|
||||
<!DOCTYPE HTML>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<title>SABnzbd $version - $T('queued'): $mbleft $T('MB')</title>
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta name="robots" content="noindex">
|
||||
<!--[if lt IE 9]>
|
||||
<script src="//html5shiv.googlecode.com/svn/trunk/html5.js"></script>
|
||||
<![endif]-->
|
||||
|
||||
#if $pane == "Config"#
|
||||
#set global $root = '../'#
|
||||
#else#
|
||||
#set global $root = '../../'#
|
||||
#end if#
|
||||
|
||||
<link rel="shortcut icon" href="${root}staticcfg/ico/favicon.ico">
|
||||
<link rel="apple-touch-icon-precomposed" sizes="144x144" href="${root}staticcfg/ico/apple-touch-icon-144x144-precomposed.png">
|
||||
<link rel="apple-touch-icon-precomposed" sizes="114x114" href="${root}staticcfg/ico/apple-touch-icon-114x114-precomposed.png">
|
||||
<link rel="apple-touch-icon-precomposed" sizes="72x72" href="${root}staticcfg/ico/apple-touch-icon-72x72-precomposed.png">
|
||||
<link rel="apple-touch-icon-precomposed" href="${root}staticcfg/ico/apple-touch-icon-57x57-precomposed.png">
|
||||
|
||||
<link rel="stylesheet" type="text/css" href="${root}staticcfg/css/style.css" />
|
||||
<script src="${root}staticcfg/js/script.js"></script>
|
||||
|
||||
<script type="text/javascript">
|
||||
\$.Browser = {
|
||||
defaults: {
|
||||
title: 'Choose Directory',
|
||||
url: '${root}api?mode=browse&output=json&apikey=$session',
|
||||
autocompleteURL: '${root}api?mode=browse&output=json&compact=1&apikey=$session'
|
||||
}
|
||||
};
|
||||
var config_pane = "$pane";
|
||||
var help_uri = "$help_uri";
|
||||
var apikey = "$session";
|
||||
var confirmWithoutSavingPrompt = "$T('Plush-confirmWithoutSavingPrompt')";
|
||||
function config_success() {
|
||||
\$('.saveButton').each(function () {
|
||||
\$(this).removeAttr("disabled").attr("value", "$T('button-saveChanges')");
|
||||
});
|
||||
}
|
||||
function config_failure() {
|
||||
\$('.saveButton').each(function () {
|
||||
\$(this).removeAttr("disabled").attr("value", "$T('smpl-failed')");
|
||||
});
|
||||
}
|
||||
|
||||
\$(document).ready(function () {
|
||||
|
||||
#if $pane != "Servers"#
|
||||
\$('.col2 H3').click(function () { \$(this).parent().next().toggle() });
|
||||
#end if#
|
||||
|
||||
\$('.sabnzbd_restart').click(function () {
|
||||
\$('.sabnzbd_restart').each(function () {
|
||||
\$(this).attr("disabled", "disabled");
|
||||
});
|
||||
var msg = "$T('explain-Restart')";
|
||||
if (confirm(msg.replace(/\<br(\s*\/|)\>/g, '\n'))) {
|
||||
\$(this).attr("value", "$T('wizard-restarting')");
|
||||
location.href = '${root}config/restart?session=$session';
|
||||
}
|
||||
\$('.sabnzbd_restart').each(function () {
|
||||
\$(this).removeAttr("disabled");
|
||||
});
|
||||
return false;
|
||||
});
|
||||
|
||||
\$('#fullform').ajaxForm({
|
||||
beforeSubmit: function () {
|
||||
\$('.saveButton').each(function () {
|
||||
\$(this).attr("disabled", "disabled").attr("value", "$T('smpl-saving')");
|
||||
});
|
||||
},
|
||||
success: function () {
|
||||
setTimeout(config_success, 1000);
|
||||
},
|
||||
error: function () {
|
||||
setTimeout(config_failure, 1000);
|
||||
},
|
||||
timeout: 3000
|
||||
});
|
||||
|
||||
\$("#sidebar-trigger").click(function () {
|
||||
if (\$("#sidebar-trigger").hasClass("trigger-left")) {
|
||||
\$("#sidebar").animate({marginLeft: "-150px", queue: false}, 250);
|
||||
\$("#sidebar-pane").animate({marginLeft: "-150px", queue: false}, 250);
|
||||
\$("#content").animate({left: "6px", queue: false}, 250);
|
||||
\$("#sidebar-trigger").removeClass("trigger-left").addClass("trigger-right");
|
||||
} else {
|
||||
\$("#sidebar").animate({marginLeft: "0px", queue: false}, 250);
|
||||
\$("#sidebar-pane").animate({marginLeft: "0px", queue: false}, 250);
|
||||
\$("#content").animate({left: "156px", queue: false}, 250);
|
||||
\$("#sidebar-trigger").removeClass("trigger-right").addClass("trigger-left");
|
||||
}
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
</script>
|
||||
|
||||
</head>
|
||||
<body class="$pane">
|
||||
<div id="sidebar">
|
||||
<a href="${root}"><img src="${root}staticcfg/images/logo.png" width="120" height="45" id="logo" alt="[home]" /></a>
|
||||
<div id="tab-container">
|
||||
<a href="${root}config/">
|
||||
<div #if $pane == "Config" then 'class="active"' else ""#>$T('menu-config')</div>
|
||||
</a>
|
||||
<a href="${root}config/general/">
|
||||
<div #if $pane == "General" then 'class="active"' else ""#>$T('cmenu-general')</div>
|
||||
</a>
|
||||
<a href="${root}config/folders/">
|
||||
<div #if $pane == "Folders" then 'class="active"' else ""#>$T('cmenu-folders')</div>
|
||||
</a>
|
||||
<a href="${root}config/switches/">
|
||||
<div #if $pane == "Switches" then 'class="active"' else ""#>$T('cmenu-switches')</div>
|
||||
</a>
|
||||
<a href="${root}config/server/">
|
||||
<div #if $pane == "Servers" then 'class="active"' else ""#>$T('cmenu-servers')</div>
|
||||
</a>
|
||||
<a href="${root}config/scheduling/">
|
||||
<div #if $pane == "Scheduling" then 'class="active"' else ""#>$T('Plush-cmenu-scheduling')</div>
|
||||
</a>
|
||||
<a href="${root}config/notify/">
|
||||
<div #if $pane == "Email" then 'class="active"' else ""#>$T('cmenu-notif')</div>
|
||||
</a>
|
||||
<!--#if 0#-->
|
||||
<a href="${root}config/indexers/">
|
||||
<div #if $pane == "Index Sites" then 'class="active"' else ""#>$T('cmenu-newzbin')</div>
|
||||
</a>
|
||||
<!--#end if#-->
|
||||
<a href="${root}config/categories/">
|
||||
<div #if $pane == "Categories" then 'class="active"' else ""#>$T('cmenu-cat')</div>
|
||||
</a>
|
||||
<a href="${root}config/sorting/">
|
||||
<div #if $pane == "Sorting" then 'class="active"' else ""#>$T('cmenu-sorting')</div>
|
||||
</a>
|
||||
<a href="${root}config/special/">
|
||||
<div #if $pane == "Special" then 'class="active"' else ""#>$T('cmenu-special')</div>
|
||||
</a>
|
||||
<a href="${root}config/rss/">
|
||||
<div #if $pane == "RSS" then 'class="active"' else ""#>$T('cmenu-rss')</div>
|
||||
</a>
|
||||
<br/>
|
||||
<a href="$helpuri$help_uri" target="_blank">
|
||||
<div>$T('menu-help')</div>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
<div id="sidebar-pane"><div id="sidebar-trigger" class="trigger-left"></div></div>
|
||||
<div id="content">
|
||||
<!-- Content start -->
|
||||
34
interfaces/Config/templates/config.tmpl
Normal file
@@ -0,0 +1,34 @@
|
||||
<!--#set global $pane="Config"#-->
|
||||
<!--#set global $help_uri="configure-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<div class="section padTable">
|
||||
<table id="infoTable">
|
||||
<tbody>
|
||||
<tr class="alt"><td class="infoTableHeader">$T('version'): </td><td class="infoTableCell">$version</td></tr>
|
||||
<tr><td class="infoTableHeader">$T('uptime'): </td><td class="infoTableCell">$uptime</td></tr>
|
||||
<tr class="alt"><td class="infoTableHeader">$T('confgFile'): </td><td class="infoTableCell">$configfn</td></tr>
|
||||
<tr><td class="infoTableHeader">$T('cache').capitalize(): </td><td class="infoTableCell"><!--#set $msg=$T('ft-buffer@2')%($cache_art, $cache_size)#-->$msg</td></tr>
|
||||
<tr class="alt"><td class="infoTableHeader">$T('parameters'): </td><td class="infoTableCell">$cmdline</td></tr>
|
||||
<tr><td class="infoTableHeader">$T('pythonVersion'): </td><td class="infoTableCell">$sys.version[:120]</td></tr>
|
||||
<tr class="infoTableSeperator alt"><td class="infoTableHeader">$T('homePage') </td><td class="infoTableCell"><a href="http://sabnzbd.org/" target="_blank">http://sabnzbd.org/</a></td></tr>
|
||||
<tr><td class="infoTableHeader">$T('menu-wiki') </td><td class="infoTableCell"><a href="http://wiki.sabnzbd.org/faq" target="_blank">http://wiki.sabnzbd.org/faq</a></td></tr>
|
||||
<tr class="alt"><td class="infoTableHeader">$T('menu-forums') </td><td class="infoTableCell"><a href="http://forums.sabnzbd.org/" target="_blank">http://forums.sabnzbd.org/</a></td></tr>
|
||||
<tr><td class="infoTableHeader">$T('source') </td><td class="infoTableCell"><a href="https://github.com/sabnzbd/sabnzbd" target="_blank">https://github.com/sabnzbd/sabnzbd</a></td></tr>
|
||||
<tr class="alt"><td class="infoTableHeader">$T('menu-irc') </td><td class="infoTableCell"><a href="irc://irc.synirc.net/#sabnzbd"><i>#sabnzbd</i> on <i>irc.synirc.net</i></a> $T('or') (<a href="http://sabnzbd.org/live-chat/" target="_blank">webchat</a>)</td></tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div class="padding alt">
|
||||
<h5 class="copyright">Copyright © 2008-2013 The SABnzbd Team <<span style="color: #0000ff;">team@sabnzbd.org</span>></h5>
|
||||
<p class="copyright"><small>$T('yourRights')</small></p>
|
||||
</div>
|
||||
<!--#if $news_items#-->
|
||||
<div class="padding">
|
||||
<iframe frameborder=0 width=100% src="http://sabnzbdplus.sourceforge.net/version/news.html"></iframe>
|
||||
</div>
|
||||
<!--#end if#-->
|
||||
</div>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
115
interfaces/Config/templates/config_cat.tmpl
Normal file
@@ -0,0 +1,115 @@
|
||||
<!--#set global $pane="Categories"#-->
|
||||
<!--#set global $help_uri="configure-categories-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
|
||||
<div class="section">
|
||||
<div class="padTable">
|
||||
<p>
|
||||
$T('explain-catTags') $T('explain-catTags2')<br/>
|
||||
</p>
|
||||
<div class="field-pair">
|
||||
<h5 class="darkred nomargin">$T('explain-relFolder'): <span class="path">$defdir</span></h5>
|
||||
</div>
|
||||
|
||||
<!--#set $odd = False#-->
|
||||
<!--#set $cur = 0#-->
|
||||
<!--#for $slot in $slotinfo#-->
|
||||
<!--#set $odd = not $odd#-->
|
||||
<!--#set $cur = $cur+1#-->
|
||||
|
||||
<form action="save" method="get">
|
||||
|
||||
<table class="catTable">
|
||||
|
||||
<!--#if $cur == 1#-->
|
||||
<tr>
|
||||
<th>$T('category')</th>
|
||||
<th>$T('priority')</th>
|
||||
<th>$T('mode')</th>
|
||||
<!--#if $script_list#--><th>$T('script')</th><!--#end if#-->
|
||||
<th>$T('catFolderPath')</th>
|
||||
<th>$T('catTags')</th>
|
||||
<th> </th>
|
||||
</tr>
|
||||
<!--#end if#-->
|
||||
|
||||
<tr class="<!--#if $odd then "alt" else ""#-->" <!--#if $slot.name == '*'#-->style="background-color: #FFFFE0;"<!--#end if#-->>
|
||||
|
||||
<td>
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" value="$slot.name" name="name" />
|
||||
<!--#if $slot.name != '*'#-->
|
||||
<input type="text" name="newname" value="$slot.name" size="10" />
|
||||
<!--#else#-->
|
||||
<input type="text" name="newname" value="$T('default')" disabled="disabled" size="10" />
|
||||
<!--#end if#-->
|
||||
</td>
|
||||
|
||||
<td>
|
||||
<select name="priority">
|
||||
<!--#if $slot.name != '*'#-->
|
||||
<option value="-100" <!--#if $slot.priority == -100 then 'selected="selected" class="selected"' else ""#-->>$T('default')</option>
|
||||
<!--#end if#-->
|
||||
<option value="2" <!--#if $slot.priority == 2 then 'selected="selected" class="selected"' else ""#-->>$T('pr-force')</option>
|
||||
<option value="1" <!--#if $slot.priority == 1 then 'selected="selected" class="selected"' else ""#-->>$T('pr-high')</option>
|
||||
<option value="0" <!--#if $slot.priority == 0 then 'selected="selected" class="selected"' else ""#-->>$T('pr-normal')</option>
|
||||
<option value="-1" <!--#if $slot.priority == -1 then 'selected="selected" class="selected"' else ""#-->>$T('pr-low')</option>
|
||||
<option value="-2" <!--#if $slot.priority == -2 then 'selected="selected" class="selected"' else ""#-->>$T('pr-paused')</option>
|
||||
</select>
|
||||
</td>
|
||||
|
||||
<td>
|
||||
<select name="pp">
|
||||
<!--#if $slot.name != '*'#-->
|
||||
<option value="" <!--#if $slot.pp == "" then 'selected="selected" class="selected"' else ""#-->>$T('default')</option>
|
||||
<!--#end if#-->
|
||||
<option value="0" <!--#if $slot.pp == "0" then 'selected="selected" class="selected"' else ""#-->>$T('pp-none')</option>
|
||||
<option value="1" <!--#if $slot.pp == "1" then 'selected="selected" class="selected"' else ""#-->>$T('pp-repair')</option>
|
||||
<option value="2" <!--#if $slot.pp == "2" then 'selected="selected" class="selected"' else ""#-->>$T('pp-unpack')</option>
|
||||
<option value="3" <!--#if $slot.pp == "3" then 'selected="selected" class="selected"' else ""#-->>$T('pp-delete')</option>
|
||||
</select>
|
||||
</td>
|
||||
|
||||
<!--#if $script_list#-->
|
||||
<td>
|
||||
<select name="script">
|
||||
<!--#for $sc in $script_list#-->
|
||||
<!--#if not ($sc == 'Default' and $slot.name == '*')#-->
|
||||
<option value="$sc" <!--#if $slot.script.lower() == $sc.lower() then 'selected="selected" class="selected"' else ""#-->>$Tspec($sc)</option>
|
||||
<!--#end if#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</td>
|
||||
<!--#end if#-->
|
||||
|
||||
<td><input type="text" name="dir" value="$slot.dir" size="30" /></td>
|
||||
<td><input type="text" name="newzbin" value="$slot.newzbin" size="30" /></td>
|
||||
|
||||
<td class="nowrap">
|
||||
<input type="submit" class="Save" value="<!--#if $cur == 2 then $T('button-add') else $T('button-save')#-->" />
|
||||
<!--#if $slot.name and $slot.name != '*'#-->
|
||||
<input type="button" class="delCat" value="$T('button-x')" />
|
||||
<!--#end if#-->
|
||||
</td>
|
||||
|
||||
</tr>
|
||||
</table>
|
||||
</form>
|
||||
<!--#end for#-->
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
\$('.delCat').click(function(){
|
||||
var theForm = \$(this).closest("form");
|
||||
theForm.attr("action", "delete").submit();
|
||||
});
|
||||
});
|
||||
</script>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
118
interfaces/Config/templates/config_folders.tmpl
Normal file
@@ -0,0 +1,118 @@
|
||||
<!--#set global $pane="Folders"#-->
|
||||
<!--#set global $help_uri="configure-folders-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="saveDirectories" method="post" name="fullform" id="fullform">
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('userFolders')</h3>
|
||||
<p>$T('explain-folderConfig')</p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<h5 class="darkred nomargin">$T('base-folder'): <span class="path">$my_home</span></h5>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="download_dir">$T('opt-download_dir')</label>
|
||||
<input type="text" name="download_dir" id="download_dir" value="$download_dir" size="45" />
|
||||
<span class="desc">$T('explain-download_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="download_free">$T('opt-download_free')</label>
|
||||
<input type="text" name="download_free" id="download_free" value="$download_free" size="8" />
|
||||
<span class="desc">$T('explain-download_free')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="complete_dir">$T('opt-complete_dir')</label>
|
||||
<input type="text" name="complete_dir" id="complete_dir" value="$complete_dir" size="45" />
|
||||
<span class="desc">$T('explain-complete_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair <!--#if $nt then "disabled" else "" #-->">
|
||||
<label class="config" for="permissions">$T('opt-permissions')</label>
|
||||
<input type="text" name="permissions" id="permissions" value="$permissions" size="8" <!--#if $nt then 'readonly="readonly" disabled="disabled"' else "" #--> />
|
||||
<span class="desc">$T('explain-permissions')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="dirscan_dir">$T('opt-dirscan_dir')</label>
|
||||
<input type="text" name="dirscan_dir" id="dirscan_dir" value="$dirscan_dir" size="45" />
|
||||
<span class="desc">$T('explain-dirscan_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="dirscan_speed">$T('opt-dirscan_speed')</label>
|
||||
<input type="number" name="dirscan_speed" id="dirscan_speed" value="$dirscan_speed" size="8" min="0" max="3600" />
|
||||
<span class="desc">$T('explain-dirscan_speed')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="script_dir">$T('opt-script_dir')</label>
|
||||
<input type="text" name="script_dir" id="script_dir" value="$script_dir" size="45" />
|
||||
<span class="desc">$T('explain-script_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="email_dir">$T('opt-email_dir')</label>
|
||||
<input type="text" name="email_dir" id="email_dir" value="$email_dir" size="45" />
|
||||
<span class="desc">$T('explain-email_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="password_file">$T('opt-password_file')</label>
|
||||
<input type="text" name="password_file" id="password_file" value="$password_file" size="45" />
|
||||
<span class="desc">$T('explain-password_file')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('systemFolders')</h3>
|
||||
<p>$T('explain-folderConfig')</p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<h5 class="darkred nomargin">$T('base-folder'): <span class="path">$my_lcldata</span></h5>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="admin_dir">$T('opt-admin_dir')</label>
|
||||
<input type="text" name="admin_dir" id="admin_dir" value="$admin_dir" size="45" />
|
||||
<span class="desc">$T('explain-admin_dir1')</span>
|
||||
<span class="desc">$T('explain-admin_dir2')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="log_dir">$T('opt-log_dir')</label>
|
||||
<input type="text" name="log_dir" id="log_dir" value="$log_dir" size="45" />
|
||||
<span class="desc">$T('explain-log_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="nzb_backup_dir">$T('opt-nzb_backup_dir')</label>
|
||||
<input type="text" name="nzb_backup_dir" id="nzb_backup_dir" value="$nzb_backup_dir" size="45" />
|
||||
<span class="desc">$T('explain-nzb_backup_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="padding alt">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</form>
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
\$('#download_dir').fileBrowser({ title: 'Select $T('opt-download_dir')' });
|
||||
\$('#complete_dir').fileBrowser({ title: 'Select $T('opt-complete_dir')' });
|
||||
\$('#dirscan_dir').fileBrowser({ title: 'Select $T('opt-dirscan_dir')' });
|
||||
\$('#script_dir').fileBrowser({ title: 'Select $T('opt-script_dir')' });
|
||||
\$('#email_dir').fileBrowser({ title: 'Select $T('opt-email_dir')' });
|
||||
});
|
||||
</script>
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
236
interfaces/Config/templates/config_general.tmpl
Normal file
@@ -0,0 +1,236 @@
|
||||
<!--#set global $pane="General"#-->
|
||||
<!--#set global $help_uri="configure-general-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="saveGeneral" method="post" name="fullform" id="fullform" novalidate>
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('webServer')</h3>
|
||||
<p><b>$T('restartRequired')</b></p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="host">$T('opt-host')</label>
|
||||
<input type="url" name="host" id="host" value="$host" size="40" />
|
||||
<span class="desc">$T('explain-host')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="port">$T('opt-port')</label>
|
||||
<input type="text" name="port" id="port" value="$port" size="8" />
|
||||
<span class="desc">$T('explain-port')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="username">$T('opt-web_username')</label>
|
||||
<input type="text" name="username" id="username" value="$username" size="30" />
|
||||
<span class="desc">$T('explain-web_username')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="password">$T('opt-web_password')</label>
|
||||
<input type="password" name="password" id="password" value="$password" size="30" />
|
||||
<span class="desc">$T('explain-web_password')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="web_dir">$T('opt-web_dir')</label>
|
||||
<select name="web_dir" id="web_dir">
|
||||
<!--#for $webline in $web_list#-->
|
||||
<!--#if $webline.lower() == $web_dir.lower()#-->
|
||||
<option value="$webline" selected="selected" class="selected">$webline</option>
|
||||
<!--#else#-->
|
||||
<option value="$webline">$webline</option>
|
||||
<!--#end if#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
<span class="desc">$T('explain-web_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="web_dir2">$T('opt-web_dir2')</label>
|
||||
<select name="web_dir2" id="web_dir2">
|
||||
<!--#for $webline in $web_list2#-->
|
||||
<!--#if $webline.lower() == $web_dir2.lower()#-->
|
||||
<option value="$webline" selected="selected" class="selected">$webline</option>
|
||||
<!--#else#-->
|
||||
<option value="$webline">$webline</option>
|
||||
<!--#end if#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
<span class="desc">$T('explain-web_dir2')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="language">$T('opt-language')</label>
|
||||
<select name="language" id="language" id="language" class="select">
|
||||
<!--#for $webline in $lang_list#-->
|
||||
<!--#if $webline[0].lower() == $language.lower()#-->
|
||||
<option value="$webline[0]" selected="selected" class="selected">$webline[1]</option>
|
||||
<!--#else#-->
|
||||
<option value="$webline[0]">$webline[1]</option>
|
||||
<!--#end if#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
<span class="desc">$T('explain-language')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="disable_api_key">$T('opt-disableApikey')</label>
|
||||
<input type="checkbox" name="disable_api_key" id="disable_api_key" value="1" <!--#if int($disable_api_key) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-disableApikey')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="apikey">$T('opt-apikey')</label>
|
||||
<input type="text" id="apikey" value="$session" size="35" />
|
||||
<input type="button" value="$T('button-apikey')" id="generate_new_apikey" />
|
||||
<input type="button" value="$T('qr-code')" title="$T('explain-qr-code')" class="show_qrcode" rel="$session" />
|
||||
<span class="desc">$T('explain-apikey')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="nzbkey">$T('opt-nzbkey')</label>
|
||||
<input type="text" id="nzbkey" value="$nzb_key" size="35" />
|
||||
<input type="button" value="$T('button-apikey')" id="generate_new_nzbkey" />
|
||||
<input type="button" value="$T('qr-code')" title="$T('explain-qr-code')" class="show_qrcode" rel="$nzb_key" />
|
||||
<span class="desc">$T('explain-nzbkey')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('httpsSupport')</h3>
|
||||
<p><b>$T('restartRequired')</b></p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<h5 class="darkred nomargin">$T('base-folder'): <span class="path">$my_lcldata</span></h5>
|
||||
</div>
|
||||
<div class="field-pair alt <!--#if int($have_ssl) == 0 then "disabled" else ""#-->">
|
||||
<label class="config" for="enable_https">$T('opt-enable_https')</label>
|
||||
<input type="checkbox" name="enable_https" id="enable_https" value="1" <!--#if int($enable_https) > 0 then 'checked="checked"' else ""#--> <!--#if int($have_ssl) == 0 then "disabled" else ""#--> />
|
||||
<span class="desc">$T('explain-enable_https')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="https_port">$T('opt-https_port')</label>
|
||||
<input type="text" name="https_port" id="https_port" value="$https_port" size="8" />
|
||||
<span class="desc">$T('explain-https_port')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="https_cert">$T('opt-https_cert')</label>
|
||||
<input type="text" name="https_cert" id="https_cert" value="$https_cert" size="50" />
|
||||
<span class="desc">$T('explain-https_cert')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="https_key">$T('opt-https_key')</label>
|
||||
<input type="text" name="https_key" id="https_key" value="$https_key" size="50" />
|
||||
<span class="desc">$T('explain-https_key')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="https_chain">$T('opt-https_chain')</label>
|
||||
<input type="text" name="https_chain" id="https_chain" value="$https_chain" size="50" />
|
||||
<span class="desc">$T('explain-https_chain')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('tuning')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="bandwidth_limit">$T('opt-bandwidth_limit')</label>
|
||||
<input type="number" name="bandwidth_limit" id="bandwidth_limit" value="$bandwidth_limit" size="8" step="1024" min="0" />
|
||||
<span class="desc">$T('explain-bandwidth_limit')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="cache_limit">$T('opt-cache_limitstr')</label>
|
||||
<input type="text" name="cache_limit" id="cache_limit" value="$cache_limit" size="8" />
|
||||
<span class="desc">$T('explain-cache_limitstr')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="cleanup_list">$T('opt-cleanup_list')</label>
|
||||
<input type="text" name="cleanup_list" id="cleanup_list" value="$cleanup_list" size="50"/>
|
||||
<span class="desc">$T('explain-cleanup_list')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="padding alt">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</form>
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
\$('#apikey, #nzbkey').click(function () { \$(this).select() });
|
||||
\$('#generate_new_apikey').click(function () {
|
||||
if (confirm("$T('Plush-confirm')")) {
|
||||
$.ajax({
|
||||
type: "POST",
|
||||
url: "../../tapi",
|
||||
data: {mode:'config', name:'set_apikey', apikey: \$('#apikey').val()},
|
||||
success: function(msg){
|
||||
\$('#apikey').val(msg);
|
||||
window.location.reload();
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
\$('#generate_new_nzbkey').click(function () {
|
||||
if (confirm("$T('Plush-confirm')")) {
|
||||
$.ajax({
|
||||
type: "POST",
|
||||
url: "../../tapi",
|
||||
data: {mode:'config', name:'set_nzbkey', apikey: \$('#apikey').val()},
|
||||
success: function(msg){
|
||||
\$('#nzbkey').val(msg);
|
||||
window.location.reload();
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
\$('.show_qrcode').each(function () {
|
||||
var qrkey = \$(this).attr('rel'),
|
||||
qrcode = \$('<img />', {
|
||||
src: 'https://chart.googleapis.com/chart?chs=300x300&cht=qr&chl=' + qrkey,
|
||||
alt: 'loading...',
|
||||
width: 300,
|
||||
height: 300
|
||||
});
|
||||
\$(this).qtip( {
|
||||
content: {
|
||||
text: qrcode
|
||||
},
|
||||
position: {
|
||||
my: 'center',
|
||||
at: 'center',
|
||||
target: \$(window)
|
||||
},
|
||||
show: {
|
||||
event: 'click',
|
||||
solo: true,
|
||||
modal: true
|
||||
},
|
||||
hide: false,
|
||||
style: 'ui-tooltip-light ui-tooltip-rounded ui-tooltip-shadow ui-tooltip-qrcode'
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
</script>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
79
interfaces/Config/templates/config_indexers.tmpl
Normal file
@@ -0,0 +1,79 @@
|
||||
<!--#set global $pane="Index Sites"#-->
|
||||
<!--#set global $help_uri="configure-indexers-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="saveNewzbin" method="post" name="fullform" id="fullform">
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>NzbMatrix $T('accountInfo')</h3>
|
||||
<p>$T('explain-nzbmatrix')</p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="matrix_username">$T('opt-username_matrix')</label>
|
||||
<input type="text" name="matrix_username" id="matrix_username" value="$matrix_username" size="30" />
|
||||
<span class="desc">$T('explain-username_matrix')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="matrix_apikey">$T('opt-apikey_matrix')</label>
|
||||
<input type="text" name="matrix_apikey" id="matrix_apikey" value="$matrix_apikey" size="35" />
|
||||
<span class="desc">$T('explain-apikey_matrix')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="matrix_del_bookmark">$T('opt-newzbin_unbookmark')</label>
|
||||
<input type="checkbox" name="matrix_del_bookmark" id="matrix_del_bookmark" value="1" <!--#if int($matrix_del_bookmark) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-newzbin_unbookmark')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="padding alt">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</form>
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
\$('#matrix_apikey').click(function(){ \$(this).select() });
|
||||
\$('#getBookmarks2').click(function(){ window.location='getBookmarks?session='+apikey; });
|
||||
\$('#hideBookmarks').click(function(){ window.location='hideBookmarks?session='+apikey; });
|
||||
\$('#showBookmarks').click(function(){ window.location='showBookmarks?session='+apikey; });
|
||||
});
|
||||
</script>
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
\$('#getBookmarks').click(function(event){
|
||||
\$.ajax({
|
||||
type: "GET",
|
||||
url: "../../tapi",
|
||||
data: {mode: 'newzbin', name: 'get_bookmarks', output: 'json', apikey: '$session' },
|
||||
beforeSend: function(){
|
||||
\$('#getBookmarks').attr("disabled", "disabled");
|
||||
\$('#getBookmarks-result').removeClass("success failure").addClass("loading");
|
||||
},
|
||||
complete: function(){
|
||||
\$('#getBookmarks').removeAttr("disabled");
|
||||
\$('#getBookmarks-result').removeClass("loading");
|
||||
},
|
||||
success: function(data){
|
||||
if(data.status == true)
|
||||
\$('#getBookmarks-result').addClass("success");
|
||||
else {
|
||||
\$('#getBookmarks-result').addClass("failure")
|
||||
alert(data.error);
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
</script>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
189
interfaces/Config/templates/config_notify.tmpl
Normal file
@@ -0,0 +1,189 @@
|
||||
<!--#set global $pane="Email"#-->
|
||||
<!--#set global $help_uri="configure-notifications-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="saveEmail" method="post" name="fullform" id="fullform" novalidate>
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('emailOptions')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="email_endjob_radio">$T('opt-email_endjob')</label>
|
||||
<select name="email_endjob" id="email_endjob">
|
||||
<option value="0" <!--#if int($email_endjob) == 0 then 'selected="selected" class="selected"' else ""#--> >$T('email-never')</option>
|
||||
<option value="1" <!--#if int($email_endjob) == 1 then 'selected="selected" class="selected"' else ""#--> >$T('email-always')</option>
|
||||
<option value="2" <!--#if int($email_endjob) == 2 then 'selected="selected" class="selected"' else ""#--> >$T('email-errorOnly')</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="email_full">$T('opt-email_full')</label>
|
||||
<input type="checkbox" name="email_full" id="email_full" value="1" <!--#if int($email_full) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-email_full')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="email_rss">$T('opt-email_rss')</label>
|
||||
<input type="checkbox" name="email_rss" id="email_rss" value="1" <!--#if int($email_rss) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-email_rss')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="email_dir">$T('opt-email_dir')</label>
|
||||
<input type="text" name="email_dir" id="email_dir" value="$email_dir" size="45" />
|
||||
<span class="desc">$T('explain-email_dir')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('emailAccount')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="email_server">$T('opt-email_server')</label>
|
||||
<input type="text" name="email_server" id="email_server" value="$email_server" size="40" />
|
||||
<span class="desc">$T('explain-email_server')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="email_to">$T('opt-email_to')</label>
|
||||
<input type="email" name="email_to" id="email_to" value="$email_to" size="40" />
|
||||
<span class="desc">$T('explain-email_to')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="email_from">$T('opt-email_from')</label>
|
||||
<input type="email" name="email_from" id="email_from" value="$email_from" size="40" />
|
||||
<span class="desc">$T('explain-email_from')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="email_account">$T('opt-email_account')</label>
|
||||
<input type="email" name="email_account" id="email_account" value="$email_account" size="30" />
|
||||
<span class="desc">$T('explain-email_account')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="email_pwd">$T('opt-email_pwd')</label>
|
||||
<input type="password" name="email_pwd" id="email_pwd" value="$email_pwd" size="30" />
|
||||
<span class="desc">$T('explain-email_pwd')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('link-testEmail')" id="test_email" rel="$T('askTestEmail')" />
|
||||
<span id="testmail-result" class="icon path darkred"> </span>
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('growlSettings')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="notify_classes">$T('opt-notify_classes')</label>
|
||||
<select name="notify_classes" multiple="multiple" class="multiple_cats">
|
||||
<!--#for $item in $notify_list#-->
|
||||
<option value="$item" <!--#if $item in $notify_classes then 'selected="selected"' else ""#--> >$T($notify_texts[$item])</option>
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
<span class="desc">$T('explain-notify_classes')</span>
|
||||
</div>
|
||||
<div class="field-pair <!--#if not $have_ncenter then "disabled" else "" #-->">
|
||||
<label class="config" for="ncenter_enable">$T('opt-ncenter_enable')</label>
|
||||
<input type="checkbox" name="ncenter_enable" id="ncenter_enable" value="1" <!--#if int($ncenter_enable) > 0 then 'checked="checked"' else ""#--> <!--#if not $have_ncenter then 'readonly="readonly" disabled="disabled"' else "" #--> />
|
||||
<span class="desc">$T('explain-ncenter_enable')</span>
|
||||
</div>
|
||||
<div class="field-pair alt <!--#if not $have_ntfosd then "disabled" else "" #-->">
|
||||
<label class="config" for="ntfosd_enable">$T('opt-ntfosd_enable')</label>
|
||||
<input type="checkbox" name="ntfosd_enable" id="ntfosd_enable" value="1" <!--#if int($ntfosd_enable) > 0 then 'checked="checked"' else ""#--> <!--#if not $have_ntfosd then 'readonly="readonly" disabled="disabled"' else "" #--> />
|
||||
<span class="desc">$T('explain-ntfosd_enable')</span>
|
||||
</div>
|
||||
<div class="field-pair" >
|
||||
<label class="config" for="growl_enable">$T('opt-growl_enable')</label>
|
||||
<input type="checkbox" name="growl_enable" id="growl_enable" value="1" <!--#if int($growl_enable) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-growl_enable')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="growl_server">$T('opt-growl_server')</label>
|
||||
<input type="text" name="growl_server" id="growl_server" value="$growl_server" size="40" />
|
||||
<span class="desc">$T('explain-growl_server')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="growl_password">$T('opt-growl_password')</label>
|
||||
<input type="password" name="growl_password" id="growl_password" value="$growl_password" size="30" />
|
||||
<span class="desc">$T('explain-growl_password')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('testNotify')" id="test_notification" />
|
||||
<span id="testnotice-result" class="icon path darkred"> </span>
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="padding alt">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</form>
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
\$('#email_dir').fileBrowser({ title: 'Select $T('opt-email_dir')' });
|
||||
\$('#test_email').click(function () {
|
||||
if (confirm(\$('#test_email').attr('rel'))) {
|
||||
\$.ajax({
|
||||
type: "GET",
|
||||
url: "../../tapi",
|
||||
data: {mode: 'test_email', apikey: '$session', output: 'json' },
|
||||
beforeSend: function () {
|
||||
\$('#test_email').attr("disabled", "disabled");
|
||||
\$('#testmail-result').removeClass("success failure").addClass("loading").html('$T('post-Verifying')');
|
||||
},
|
||||
complete: function () {
|
||||
\$('#test_email').removeAttr("disabled");
|
||||
\$('#testmail-result').removeClass("loading");
|
||||
},
|
||||
success: function (data) {
|
||||
if (data.status == true) {
|
||||
\$('#testmail-result').addClass("success").html('$T('smpl-emailsent')');
|
||||
} else {
|
||||
\$('#testmail-result').addClass("failure").html(data.error);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
\$('#test_notification').click(function () {
|
||||
\$.ajax({
|
||||
type: "GET",
|
||||
url: "../../tapi",
|
||||
data: {mode: 'test_notif', apikey: '$session', output: 'json' },
|
||||
beforeSend: function () {
|
||||
\$('#test_notification').attr("disabled", "disabled");
|
||||
\$('#testnotice-result').removeClass("success failure").addClass("loading").html('$T('post-Verifying')');
|
||||
},
|
||||
complete: function () {
|
||||
\$('#test_notification').removeAttr("disabled");
|
||||
\$('#testnotice-result').removeClass("loading");
|
||||
},
|
||||
success: function (data) {
|
||||
if (data.status == true) {
|
||||
\$('#testnotice-result').addClass("success").html('$T('smpl-notesent')');
|
||||
} else {
|
||||
\$('#testnotice-result').addClass("failure").html(data.error);
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
</script>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
575
interfaces/Config/templates/config_rss.tmpl
Normal file
@@ -0,0 +1,575 @@
|
||||
<!--#set global $pane="RSS"#-->
|
||||
<!--#set global $help_uri="configure-rss-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<!--#if not $active_feed#-->
|
||||
<div class="section">
|
||||
<div class="padTable">
|
||||
|
||||
<p>$T('explain-RSS')</p>
|
||||
|
||||
<form action="add_rss_feed" method="post" novalidate>
|
||||
<input type="hidden" name="session" value="$session">
|
||||
<table class="catTable">
|
||||
<tr>
|
||||
<th> </th>
|
||||
<th>$T('name')</th>
|
||||
<th>$T('feed') URL</th>
|
||||
<th> </th>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td><input type="checkbox" name="enable" value="1" /></td>
|
||||
<td><input type="text" name="feed" size="20" value="$feed" placeholder="unique feed name" /></td>
|
||||
<td><input type="url" name="uri" size="35" /></td>
|
||||
<td class="nowrap">
|
||||
<input type="submit" class="Save" value="$T('button-add')" />
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</form>
|
||||
|
||||
<br/>
|
||||
|
||||
<form action="save_rss_feed" method="post" novalidate>
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<table id="subscriptions">
|
||||
<tbody>
|
||||
|
||||
<!--#set $feeds = sorted($rss.keys(), cmp=lambda x,y: cmp(x.lower(), y.lower()))#--><!--#slurp#-->
|
||||
<!--#set $odd = False#--><!--#slurp#-->
|
||||
<!--#for $feed_item in $feeds#--><!--#slurp#-->
|
||||
<!--#set $odd = not $odd#--><!--#slurp#-->
|
||||
|
||||
<tr class="data-row <!--#if $odd then "alt" else ""#-->" >
|
||||
<td class="chk">
|
||||
<input type="checkbox" class="toggleFeedCheckbox" name="enable" value="1" <!--#if int($rss[$feed_item]['enable']) != 0 then 'checked="checked"' else ""#--> rel="$feed_item" />
|
||||
</td>
|
||||
<td class="title">
|
||||
<div class="subscription-title">
|
||||
<a href="?feed=$rss[$feed_item]['link']" class="path feed">
|
||||
<div class="favicon" style="background-image: url("http://www.google.com/s2/favicons?domain=$rss[$feed_item]['baselink']&alt=feed");"></div>
|
||||
<span class="<!--#if int($rss[$feed_item]['enable']) != 0 then 'feed_enabled"' else "feed_disabled"#-->">$feed_item</span>
|
||||
</a>
|
||||
</div>
|
||||
<!-- <input type="text" name="newfeed" value="$feed_item" size="25" readonly="readonly" class="readonly" /> -->
|
||||
</td>
|
||||
<td class="controls">
|
||||
<input type="button" class="testFeed" value="$T('Read')" rel="$feed_item" />
|
||||
<input type="hidden" name="uri" value="$rss[$feed_item]['uri']" size="75" />
|
||||
<input type="button" class="editFeed" value="$T('Edit') URL" rel="$feed_item" />
|
||||
<input type="button" class="delFeed" value="$T('button-x')" rel="$feed_item" />
|
||||
</td>
|
||||
</tr>
|
||||
<tr class="feed-row <!--#if $odd then "alt" else ""#-->">
|
||||
<td></td>
|
||||
<td colspan="2">
|
||||
<div>$rss[$feed_item]['uri']</div>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<!--#end for#-->
|
||||
|
||||
</tbody>
|
||||
</table>
|
||||
</form>
|
||||
|
||||
<!--#if $feeds#-->
|
||||
<br/>
|
||||
|
||||
<form action="rss_now" method="post" novalidate>
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="submit" class="readAll" value="$T('button-rssNow')" />
|
||||
</form>
|
||||
<!--#end if#-->
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="section">
|
||||
<form action="save_rss_rate" method="post">
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<label class="config narrow" for="rss_rate">$T('opt-rss_rate')</label>
|
||||
<input type="number" name="rss_rate" id="rss_rate" value="$rss_rate" size="8" min="15" max="1440" />
|
||||
<input type="submit" value="$T('button-save')" />
|
||||
<span class="desc narrow">$T('explain-rss_rate')</span>
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</form>
|
||||
</div>
|
||||
|
||||
<!--#end if#-->
|
||||
|
||||
<!--#if $active_feed#-->
|
||||
<!--#set $feed = $active_feed#-->
|
||||
|
||||
<div class="section">
|
||||
<div class="padTable">
|
||||
<h2 class="nomargin activeRSS"><a href="${root}config/rss/">$T('cmenu-rss')</a> » <a href="$rss[$active_feed]['uri']" onclick="window.open(this.href); return false;">$active_feed</a></h2>
|
||||
<!--#if $error#-->
|
||||
<h3 class="darkred">$error</h3>
|
||||
<!--#end if#-->
|
||||
|
||||
<form action="upd_rss_feed" method="post">
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" name="feed" value="$feed" />
|
||||
<input type="hidden" name="uri" value="$rss[$feed]['uri']" />
|
||||
<table class="catTable">
|
||||
<thead>
|
||||
<tr>
|
||||
<th> </th>
|
||||
<th>$T('rss-order')</th>
|
||||
<th>$T('rss-type')</th>
|
||||
<th>$T('rss-filter')</th>
|
||||
<!--#if $rss[$feed]['pick_cat']#-->
|
||||
<th>$T('category')</th>
|
||||
<!--#end if#-->
|
||||
<th>$T('priority')</th>
|
||||
<th>$T('mode')</th>
|
||||
<!--#if $rss[$feed]['pick_script']#-->
|
||||
<th>$T('script')</th>
|
||||
<!--#end if#-->
|
||||
<th> </th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<!-- default / global filter -->
|
||||
<tbody>
|
||||
<tr class="default">
|
||||
<td>
|
||||
<input type="checkbox" disabled="disabled" class="hidden" />
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" disabled="disabled" size="1" class="hidden" />
|
||||
</td>
|
||||
<td>
|
||||
<select name="filter_type" disabled="disabled" class="hidden" >
|
||||
<option value="A" selected="selected"> $T('rss-accept')</option>
|
||||
<option value="M"> $T('rss-must')</option>
|
||||
<option value="R"> $T('rss-reject')</option>
|
||||
<option value="C"> $T('rss-mustcat')</option>
|
||||
</select>
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" disabled="disabled" value="" size="25" class="hidden" />
|
||||
</td>
|
||||
<!--#if $rss[$feed]['pick_cat']#-->
|
||||
<td>
|
||||
<select name="cat">
|
||||
<!--#for $ct in $cat_list#-->
|
||||
<option value="$ct" <!--#if $ct == $rss[$feed]['cat'] then 'selected="selected"' else ""#-->>$Tspec($ct)</option><!--#slurp#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</td>
|
||||
<!--#end if#-->
|
||||
<td>
|
||||
<select name="priority">
|
||||
<option value="-100" <!--#if $rss[$feed]['priority'] == -100 then 'selected="selected"' else ''#-->>$T('default')</option>
|
||||
<option value="2" <!--#if $rss[$feed]['priority'] == 2 then 'selected="selected"' else ''#-->>$T('pr-force')</option>
|
||||
<option value="1" <!--#if $rss[$feed]['priority'] == 1 then 'selected="selected"' else ''#-->>$T('pr-high')</option>
|
||||
<option value="0" <!--#if $rss[$feed]['priority'] == 0 then 'selected="selected"' else ''#-->>$T('pr-normal')</option>
|
||||
<option value="-1" <!--#if $rss[$feed]['priority'] == -1 then 'selected="selected"' else ''#-->>$T('pr-low')</option>
|
||||
<option value="-2" <!--#if $rss[$feed]['priority'] == -2 then 'selected="selected"' else ''#-->>$T('pr-paused')</option>
|
||||
</select>
|
||||
</td>
|
||||
<td>
|
||||
<select name="pp">
|
||||
<option value="" <!--#if $rss[$feed]['pp'] == "" then 'selected="selected"' else ''#-->>$T('default')</option>
|
||||
<option value="0" <!--#if $rss[$feed]['pp'] == "0" then 'selected="selected"' else ''#-->>$T('pp-none')</option>
|
||||
<option value="1" <!--#if $rss[$feed]['pp'] == "1" then 'selected="selected"' else ''#-->>$T('pp-repair')</option>
|
||||
<option value="2" <!--#if $rss[$feed]['pp'] == "2" then 'selected="selected"' else ''#-->>$T('pp-unpack')</option>
|
||||
<option value="3" <!--#if $rss[$feed]['pp'] == "3" then 'selected="selected"' else ''#-->>$T('pp-delete')</option>
|
||||
</select>
|
||||
</td>
|
||||
<!--#if $rss[$feed]['pick_script']#-->
|
||||
<td>
|
||||
<select name="script">
|
||||
<!--#for $sc in $script_list#-->
|
||||
<option value="$sc" <!--#if $sc == $rss[$feed]['script'] then 'selected="selected"' else ""#-->>$Tspec($sc)</option><!--#slurp#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</td>
|
||||
<!--#end if#-->
|
||||
<td>
|
||||
<input type="submit" class="Save" value="$T('button-save')" />
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</form>
|
||||
|
||||
<!-- add new filter -->
|
||||
<form action="upd_rss_filter" method="post">
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" name="index" value="$rss[$feed]['filtercount']" />
|
||||
<input type="hidden" name="feed" value="$feed" />
|
||||
<table class="catTable">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<input type="checkbox" name="enabled" value="1" checked="checked" />
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" name="new_index" size="1" />
|
||||
</td>
|
||||
<td>
|
||||
<select name="filter_type">
|
||||
<option value="A" selected="selected"> $T('rss-accept')</option>
|
||||
<option value="M"> $T('rss-must')</option>
|
||||
<option value="R"> $T('rss-reject')</option>
|
||||
<option value="C"> $T('rss-mustcat')</option>
|
||||
</select>
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" name="filter_text" value="" size="25" />
|
||||
</td>
|
||||
<!--#if $rss[$feed]['pick_cat']#-->
|
||||
<td>
|
||||
<select name="cat">
|
||||
<!--#for $ct in $cat_list#-->
|
||||
<option value="$ct" <!--#if $ct == 'Default' then 'selected="selected"' else ""#-->>$Tspec($ct)</option><!--#slurp#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</td>
|
||||
<!--#end if#-->
|
||||
<td>
|
||||
<select name="priority">
|
||||
<option value="-100" selected="selected">$T('default')</option>
|
||||
<option value="2">$T('pr-force')</option>
|
||||
<option value="1">$T('pr-high')</option>
|
||||
<option value="0">$T('pr-normal')</option>
|
||||
<option value="-1">$T('pr-low')</option>
|
||||
<option value="-2">$T('pr-paused')</option>
|
||||
</select>
|
||||
</td>
|
||||
<td>
|
||||
<select name="pp">
|
||||
<option value="" selected="selected">$T('default')</option>
|
||||
<option value="0">$T('pp-none')</option>
|
||||
<option value="1">$T('pp-repair')</option>
|
||||
<option value="2">$T('pp-unpack')</option>
|
||||
<option value="3">$T('pp-delete')</option>
|
||||
</select>
|
||||
</td>
|
||||
<!--#if $rss[$feed]['pick_script']#-->
|
||||
<td>
|
||||
<select name="script">
|
||||
<!--#for $sc in $script_list#-->
|
||||
<option value="$sc" <!--#if $sc == 'Default' then 'selected="selected"' else ""#-->>$Tspec($sc)</option><!--#slurp#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</td>
|
||||
<!--#end if#-->
|
||||
<td>
|
||||
<input type="submit" class="Save" value="$T('button-add')" />
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</form>
|
||||
|
||||
<!--#set $odd = False#--><!--#slurp#-->
|
||||
<!--#set $fnum = 0#--><!--#slurp#-->
|
||||
<!--#for $filter in $rss[$feed].filters#--><!--#slurp#-->
|
||||
<!--#set $odd = not $odd#--><!--#slurp#-->
|
||||
|
||||
<form action="upd_rss_filter" method="post">
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" name="index" value="$fnum" />
|
||||
<input type="hidden" name="feed" value="$feed" />
|
||||
<table class="catTable">
|
||||
<tbody>
|
||||
<tr class="<!--#if $odd then "alt" else ""#-->">
|
||||
<td>
|
||||
<input type="checkbox" name="enabled" value="1" <!--#if $filter[6] == '1' then 'checked="checked"' else ""#--> />
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" name="new_index" value="$fnum" size="1" />
|
||||
</td>
|
||||
<td>
|
||||
<select name="filter_type">
|
||||
<option value="A" <!--#if $filter[3] == "A" then 'selected="selected"' else ""#-->> $T('rss-accept')</option>
|
||||
<option value="M" <!--#if $filter[3] == "M" then 'selected="selected"' else ""#-->> $T('rss-must')</option>
|
||||
<option value="R" <!--#if $filter[3] == "R" then 'selected="selected"' else ""#-->> $T('rss-reject')</option>
|
||||
<option value="C" <!--#if $filter[3] == "C" then 'selected="selected"' else ""#-->> $T('rss-mustcat')</option>
|
||||
</select>
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" name="filter_text" value="$filter[4]" size="25" />
|
||||
</td>
|
||||
<!--#if $rss[$feed]['pick_cat']#-->
|
||||
<td>
|
||||
<select name="cat">
|
||||
<!--#for $ct in $cat_list#-->
|
||||
<option value="$ct" <!--#if $ct == $filter[0] then 'selected="selected"' else ""#-->>$Tspec($ct)</option><!--#slurp#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</td>
|
||||
<!--#end if#-->
|
||||
<td>
|
||||
<select name="priority">
|
||||
<option value="-100" <!--#if $filter[5] == "-100" then 'selected="selected"' else ""#-->>$T('default')</option>
|
||||
<option value="2" <!--#if $filter[5] == "2" then 'selected="selected"' else ""#-->>$T('pr-force')</option>
|
||||
<option value="1" <!--#if $filter[5] == "1" then 'selected="selected"' else ""#-->>$T('pr-high')</option>
|
||||
<option value="0" <!--#if $filter[5] == "0" then 'selected="selected"' else ""#-->>$T('pr-normal')</option>
|
||||
<option value="-1" <!--#if $filter[5] == "-1" then 'selected="selected"' else ""#-->>$T('pr-low')</option>
|
||||
<option value="-2" <!--#if $filter[5] == "-2" then 'selected="selected"' else ""#-->>$T('pr-paused')</option>
|
||||
</select>
|
||||
</td>
|
||||
<td>
|
||||
<select name="pp">
|
||||
<option value="" <!--#if $filter[1] == "" then 'selected="selected"' else ""#-->>$T('default')</option>
|
||||
<option value="0" <!--#if $filter[1] == "0" then 'selected="selected"' else ""#-->>$T('pp-none')</option>
|
||||
<option value="1" <!--#if $filter[1] == "1" then 'selected="selected"' else ""#-->>$T('pp-repair')</option>
|
||||
<option value="2" <!--#if $filter[1] == "2" then 'selected="selected"' else ""#-->>$T('pp-unpack')</option>
|
||||
<option value="3" <!--#if $filter[1] == "3" then 'selected="selected"' else ""#-->>$T('pp-delete')</option>
|
||||
</select>
|
||||
</td>
|
||||
<!--#if $rss[$feed]['pick_script']#-->
|
||||
<td>
|
||||
<select name="script">
|
||||
<!--#for $sc in $script_list#-->
|
||||
<option value="$sc" <!--#if $sc == $filter[2] then 'selected="selected"' else ""#-->>$Tspec($sc)</option><!--#slurp#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</td>
|
||||
<!--#end if#-->
|
||||
<td>
|
||||
<input type="submit" class="Save" value="$T('button-save')" />
|
||||
<input type="button" class="delFilter" value="$T('button-x')" />
|
||||
<!--#if not $rss[$feed].filter_states[$fnum]#--> $T('Incorrect filter')<!--#end if#-->
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</form>
|
||||
|
||||
<!--#set $fnum = $fnum+1#-->
|
||||
<!--#end for#-->
|
||||
|
||||
<form action="download_rss_feed" method="post">
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" name="feed" value="$feed" />
|
||||
<div class="padding">
|
||||
<input type="button" class="testFeed" value="$T('button-preFeed')" rel="$feed" />
|
||||
<input type="submit" value="$T('button-forceFeed')" />
|
||||
<input type="button" class="cleanFeed" value="$T('button-clear') $T('link-download')" />
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<br/>
|
||||
<div style="padding-left: 10px; border-bottom: 1px solid #DFDEDE;">
|
||||
<ul class="tabs">
|
||||
<li><a href="#">$T('rss-matched') <span class="count"><!--#echo len($matched)#--></span></a></li>
|
||||
<li><a href="#">$T('rss-notMatched') <span class="count"><!--#echo len($unmatched)#--></span></a></li>
|
||||
<li><a href="#">$T('rss-done') <span class="count"><!--#echo len($downloaded)#--></span></a></li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="tab-content padTable">
|
||||
<!--#if $matched#-->
|
||||
<table class="catTable">
|
||||
|
||||
<!--#set $odd = False#--><!--#slurp#-->
|
||||
<!--#set $cur = 0#--><!--#slurp#-->
|
||||
<!--#for $job in $matched#--><!--#slurp#-->
|
||||
<!--#set $odd = not $odd#--><!--#slurp#-->
|
||||
<!--#set $cur = $cur+1#--><!--#slurp#-->
|
||||
|
||||
<!--#if $cur == 1#-->
|
||||
<thead>
|
||||
<tr>
|
||||
<th>$T('link-download')</th>
|
||||
<th>$T('rss-skip')</th>
|
||||
<th>$T('rss-filter')</th>
|
||||
<th>$T('sort-title')</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<!--#end if#-->
|
||||
<tr class="infoTableSeperator <!--#if $odd then "alt" else ""#-->">
|
||||
<td>
|
||||
<form action="download" method="get">
|
||||
<input type="hidden" value="$feed" name="feed" />
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" name="url" value="$job[0]" />
|
||||
<input type="hidden" name="nzbname" value="$job[4]" />
|
||||
<input type="submit" value="$T('link-download')" />
|
||||
</form>
|
||||
</td>
|
||||
<td class="align-center">$job[2]</td>
|
||||
<td class="align-center">
|
||||
<span>$job[3]</span>
|
||||
</td>
|
||||
<td>$job[1]</td>
|
||||
</tr>
|
||||
<!--#end for#-->
|
||||
</table>
|
||||
|
||||
<!--#else#-->
|
||||
$T('none')
|
||||
<!--#end if#-->
|
||||
</div>
|
||||
|
||||
<div class="tab-content padTable">
|
||||
<!--#if $unmatched#-->
|
||||
<table class="catTable">
|
||||
|
||||
<!--#set $odd = False#--><!--#slurp#-->
|
||||
<!--#set $cur = 0#--><!--#slurp#-->
|
||||
<!--#for $job in $unmatched#--><!--#slurp#-->
|
||||
<!--#set $odd = not $odd#--><!--#slurp#-->
|
||||
<!--#set $cur = $cur+1#--><!--#slurp#-->
|
||||
|
||||
<!--#if $cur == 1#-->
|
||||
<thead>
|
||||
<tr>
|
||||
<th>$T('link-download')</th>
|
||||
<th>$T('rss-skip')</th>
|
||||
<th>$T('rss-filter')</th>
|
||||
<th>$T('sort-title')</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<!--#end if#-->
|
||||
<tr class="infoTableSeperator <!--#if $odd then "alt" else ""#-->">
|
||||
<td>
|
||||
<form action="download" method="get">
|
||||
<input type="hidden" value="$feed" name="feed" />
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" name="url" value="$job[0]" />
|
||||
<input type="hidden" name="nzbname" value="$job[4]" />
|
||||
<input type="submit" value="$T('link-download')" />
|
||||
</form>
|
||||
</td>
|
||||
<td class="align-center">$job[2]</td>
|
||||
<td class="align-center">
|
||||
<span>$job[3]</span>
|
||||
</td>
|
||||
<td>$job[1]</td>
|
||||
</tr>
|
||||
<!--#end for#-->
|
||||
</table>
|
||||
|
||||
<!--#else#-->
|
||||
$T('none')
|
||||
<!--#end if#-->
|
||||
</div>
|
||||
|
||||
|
||||
<div class="tab-content padTable">
|
||||
<!--#if $downloaded#-->
|
||||
<form action="clean_rss_jobs" method="post">
|
||||
<input type="hidden" value="$feed" name="feed" />
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<table class="catTable">
|
||||
|
||||
<!--#set $odd = False#--><!--#slurp#-->
|
||||
<!--#set $cur = 0#--><!--#slurp#-->
|
||||
<!--#for $job in $downloaded#--><!--#slurp#-->
|
||||
<!--#set $odd = not $odd#--><!--#slurp#-->
|
||||
<!--#set $cur = $cur+1#--><!--#slurp#-->
|
||||
|
||||
<!--#if $cur == 1#-->
|
||||
<thead>
|
||||
<tr>
|
||||
<th>$T('sort-title')</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<!--#end if#-->
|
||||
<tr class="infoTableSeperator <!--#if $odd then "alt" else ""#-->">
|
||||
<td>$job</td>
|
||||
</tr>
|
||||
<!--#end for#-->
|
||||
</table>
|
||||
</form>
|
||||
|
||||
<!--#else#-->
|
||||
$T('none')
|
||||
<!--#end if#-->
|
||||
</div>
|
||||
|
||||
<!--#end if#-->
|
||||
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<script>
|
||||
function urlencode(str) {
|
||||
return encodeURIComponent(str).replace(/!/g, '%21').replace(/'/g, '%27').replace(/\(/g, '%28').replace(/\)/g, '%29').replace(/\*/g, '%2A').replace(/%20/g, '+');
|
||||
}
|
||||
|
||||
\$(document).ready(function(){
|
||||
\$('.editFeed').click(function(){
|
||||
var oldURI = \$(this).prev().val();
|
||||
var newURI = prompt("$T('feed') URL", oldURI );
|
||||
if(newURI != "" && newURI !== null) {
|
||||
var whichFeed = \$(this).attr("rel");
|
||||
\$.ajax({
|
||||
type: "POST",
|
||||
url: "save_rss_feed",
|
||||
data: {feed: whichFeed, uri: newURI, session: "$session" }
|
||||
}).done(function( msg ) {
|
||||
location.reload();
|
||||
});
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
});
|
||||
|
||||
\$('.delFeed').click(function(e){
|
||||
e.preventDefault();
|
||||
if ( confirm("$T('confirm')") ) {
|
||||
var whichFeed = \$(this).attr("rel");
|
||||
\$.ajax({
|
||||
type: "POST",
|
||||
url: "del_rss_feed",
|
||||
data: {feed: whichFeed, session: "$session" }
|
||||
}).done(function( msg ) {
|
||||
location.reload();
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
\$('.testFeed').click(function(){
|
||||
var whichFeed = \$(this).attr("rel");
|
||||
\$.ajax({
|
||||
type: "POST",
|
||||
url: "test_rss_feed",
|
||||
data: {feed: whichFeed, session: "$session" }
|
||||
}).done(function( msg ) {
|
||||
location = '?feed=' + urlencode(whichFeed);
|
||||
// location.reload();
|
||||
});
|
||||
});
|
||||
|
||||
\$('.toggleFeedCheckbox').click(function(){
|
||||
var whichFeed = \$(this).attr("rel");
|
||||
\$.ajax({
|
||||
type: "POST",
|
||||
url: "toggle_rss_feed",
|
||||
data: {feed: whichFeed, session: "$session" }
|
||||
}).done(function() {
|
||||
location.reload();
|
||||
});
|
||||
});
|
||||
|
||||
\$('.cleanFeed').click(function(){
|
||||
var theForm = \$(this).closest("form");
|
||||
theForm.attr("action", "clean_rss_jobs").submit();
|
||||
});
|
||||
\$('.delFilter').click(function(){
|
||||
var theForm = \$(this).closest("form");
|
||||
theForm.attr("action", "del_rss_filter").submit();
|
||||
});
|
||||
\$(function() {
|
||||
\$("ul.tabs").tabs("div.tab-content");
|
||||
});
|
||||
|
||||
});
|
||||
</script>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
100
interfaces/Config/templates/config_scheduling.tmpl
Normal file
@@ -0,0 +1,100 @@
|
||||
<!--#set global $pane="Scheduling"#-->
|
||||
<!--#set global $help_uri="configure-scheduling-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<%
|
||||
import time
|
||||
t = time.localtime()
|
||||
hour = t[3]
|
||||
if hour != 23:
|
||||
hour += 1
|
||||
else:
|
||||
hour = 0
|
||||
%>
|
||||
|
||||
<div class="colmask">
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('addSchedule')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<form action="addSchedule" method="post">
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="hour">$T('hour').capitalize() : $T('minute').capitalize()</label>
|
||||
<select name="hour" id="hour">
|
||||
<!--#for $i in range(24)#-->
|
||||
<option value="$i" <!--#if hour == i then 'selected="selected"' else ""#--> > $str($i).zfill(2) </option>
|
||||
<!--#end for#-->
|
||||
</select> <b>:</b> <select name="minute" id="minute">
|
||||
<!--#for $i in range(60)#-->
|
||||
<option value="$i"> $str($i).zfill(2) </option>
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="daysofweek">$T('sch-frequency')</label>
|
||||
<div class="checkbox-days">
|
||||
<p><input type="checkbox" name="daysofweek" value="1"><label>$T('monday')</label></p>
|
||||
<p><input type="checkbox" name="daysofweek" value="2"><label>$T('tuesday')</label></p>
|
||||
<p><input type="checkbox" name="daysofweek" value="3"><label>$T('wednesday')</label></p>
|
||||
<p><input type="checkbox" name="daysofweek" value="4"><label>$T('thursday')</label></p>
|
||||
<p><input type="checkbox" name="daysofweek" value="5"><label>$T('friday')</label></p>
|
||||
<p><input type="checkbox" name="daysofweek" value="6"><label>$T('saturday')</label></p>
|
||||
<p><input type="checkbox" name="daysofweek" value="7"><label>$T('sunday')</label></p>
|
||||
</div>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="action">$T('sch-action')</label>
|
||||
<select name="action" id="action">
|
||||
<!--#for $action in $actions#-->
|
||||
<option value="$action">$actions_lng[$action]</option>
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="arguments">$T('sch-arguments')</label>
|
||||
<input type="text" name="arguments" id="arguments" value="" size="20" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-addSchedule')" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
</form>
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('currentSchedules')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<!--#if $schedlines#-->
|
||||
<!--#set $schednum = 0#-->
|
||||
<!--#set $odd = True#-->
|
||||
<!--#for $line in $schedlines#-->
|
||||
<!--#set $odd = not $odd#-->
|
||||
<form action="delSchedule" method="post">
|
||||
<input type="hidden" name="session" id="session" value="$session">
|
||||
<input type="hidden" name="line" id="line" value="$line"/>
|
||||
<div class="field-pair infoTableSeperator<!--#if $odd then "" else " alt"#-->">
|
||||
<input class="float-left" type="submit" value="$T('button-x')" />
|
||||
<div class="scheduleEntry">
|
||||
<span class="time">$taskinfo[$schednum][1]:$taskinfo[$schednum][2]</span><span class="frequency">$taskinfo[$schednum][3]</span> <span class="darkred">$taskinfo[$schednum][4]</span>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
<!--#set $schednum = $schednum+1#-->
|
||||
<!--#end for#-->
|
||||
<!--#else#-->
|
||||
<div class="field-pair">
|
||||
<label class="config">$T('none')</label>
|
||||
</div>
|
||||
<!--#end if#-->
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
220
interfaces/Config/templates/config_server.tmpl
Normal file
@@ -0,0 +1,220 @@
|
||||
<!--#set global $pane="Servers"#-->
|
||||
<!--#set global $help_uri="configure-servers-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="addServer" method="post" novalidate>
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<div id="addServer">
|
||||
<div class="padding alt">
|
||||
<input type="button" value="$T('button-addServer')" id="addServerButton" />
|
||||
</div>
|
||||
</div>
|
||||
<div class="section" id="addServerContent" style="display: none;">
|
||||
<div class="col2">
|
||||
<h3>$T('addServer')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="enable">$T('srv-enable')</label>
|
||||
<input type="checkbox" name="enable" id="enable" value="1" checked="checked" />
|
||||
<span class="desc">$T('srv-enable')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="host">$T('srv-host')</label>
|
||||
<input type="text" name="host" id="host" size="40" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="port">$T('srv-port')</label>
|
||||
<input type="text" name="port" id="port" size="8" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="username">$T('srv-username')</label>
|
||||
<input type="text" name="username" id="username" size="30" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="password">$T('srv-password')</label>
|
||||
<input type="password" name="password" id="password" size="30" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="connections">$T('srv-connections')</label>
|
||||
<input type="number" name="connections" id="connections" size="8" min="0" max="100" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="retention">$T('srv-retention')</label>
|
||||
<input type="number" name="retention" id="retention" size="8" min="0" /> <i>$T('days')</i>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="timeout">$T('srv-timeout')</label>
|
||||
<input type="number" name="timeout" id="timeout" size="8" min="30" /> <i>$T('seconds')</i>
|
||||
</div>
|
||||
<div class="field-pair alt <!--#if int($have_ssl) == 0 then "disabled" else ""#-->">
|
||||
<label class="config" for="ssl">$T('srv-ssl')</label>
|
||||
<input type="checkbox" name="ssl" id="ssl" value="1" <!--#if int($have_ssl) == 0 then "disabled=\"disabled\"" else ""#--> />
|
||||
<span class="desc">$T('srv-ssl')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="fillserver">$T('srv-fillserver')</label>
|
||||
<input type="checkbox" name="fillserver" id="fillserver" value="1" />
|
||||
<span class="desc">$T('srv-fillserver')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="optional">$T('srv-optional')</label>
|
||||
<input type="checkbox" name="optional" id="optional" value="1" />
|
||||
<span class="desc">$T('srv-optional')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-addServer')" />
|
||||
<input type="button" value="$T('button-testServer')" class="testServer" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
</form>
|
||||
|
||||
<!--#set $slist = $servers.keys()#-->
|
||||
<!--#$slist.sort()#-->
|
||||
<!--#set $cur = 0#-->
|
||||
<!--#for $server in $slist#-->
|
||||
<!--#set $cur = $cur + 1#-->
|
||||
|
||||
<form action="saveServer" method="post" id="fullform" novalidate>
|
||||
<input type="hidden" name="session" value="$session" />
|
||||
<input type="hidden" name="server" value="$server" />
|
||||
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$servers[$server]['name']</h3>
|
||||
<p>
|
||||
<table><tr>
|
||||
<td><input type="checkbox" class="toggleServerCheckbox" name="q_enable" value="1" <!--#if int($servers[$server]['enable']) != 0 then 'checked="checked"' else ""#--> rel="$server" /></td>
|
||||
<td> $T('enabled')</td>
|
||||
</tr></table>
|
||||
</p>
|
||||
<input type="button" value="$T('button-clrServer')" class="clrServer" />
|
||||
<input type="button" value="$T('showDetails')" class="showserver" />
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1" style="display:none;">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="enable$cur">$T('srv-enable')</label>
|
||||
<input type="checkbox" name="enable" id="enable$cur" value="1" <!--#if int($servers[$server]['enable']) != 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('srv-enable')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="host$cur">$T('srv-host')</label>
|
||||
<input type="text" name="host" id="host$cur" value="$servers[$server]['host']" size="40" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="port$cur">$T('srv-port')</label>
|
||||
<input type="text" name="port" id="port$cur" value="$servers[$server]['port']" size="8" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="username$cur">$T('srv-username')</label>
|
||||
<input type="text" name="username" id="username$cur" value="$servers[$server]['username']" size="30" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="password$cur">$T('srv-password')</label>
|
||||
<input type="password" name="password" id="password$cur" value="$servers[$server]['password']" size="30" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="connections$cur">$T('srv-connections')</label>
|
||||
<input type="number" name="connections" id="connections$cur" value="$servers[$server]['connections']" size="8" min="0" max="100" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="retention$cur">$T('srv-retention')</label>
|
||||
<input type="number" name="retention" id="retention$cur" value="$servers[$server]['retention']" size="8" min="0" /> <i>$T('days')</i>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="timeout$cur">$T('srv-timeout')</label>
|
||||
<input type="number" name="timeout" id="timeout$cur" value="$servers[$server]['timeout']" size="8" min="30" /> <i>$T('seconds')</i>
|
||||
</div>
|
||||
<div class="field-pair alt <!--#if int($have_ssl) == 0 then "disabled" else ""#-->">
|
||||
<label class="config" for="ssl$cur">$T('srv-ssl')</label>
|
||||
<input type="checkbox" name="ssl" id="ssl$cur" value="1" <!--#if int($servers[$server]['ssl']) != 0 and int($have_ssl) == 1 then 'checked="checked"' else ""#--> <!--#if int($have_ssl) == 0 then "disabled=\"disabled\"" else ""#--> />
|
||||
<span class="desc">$T('srv-ssl')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="fillserver$cur">$T('srv-fillserver')</label>
|
||||
<input type="checkbox" name="fillserver" id="fillserver$cur" value="1" <!--#if int($servers[$server]['fillserver']) != 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('srv-fillserver')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="optional$cur">$T('srv-optional')</label>
|
||||
<input type="checkbox" name="optional" id="optional$cur" value="1" <!--#if int($servers[$server]['optional']) != 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('srv-optional')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-testServer')" class="testServer" />
|
||||
<input type="button" value="$T('button-delServer')" class="delServer" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
<div class="col2" style="display:block;">
|
||||
<!--#if 'amounts' in $servers[$server]#-->
|
||||
<b>$T('srv-bandwidth'):</b><br/>
|
||||
$T('total'): $(servers[$server]['amounts'][0])B<br/>
|
||||
$T('today'): $(servers[$server]['amounts'][3])B<br/>
|
||||
$T('thisWeek'): $(servers[$server]['amounts'][2])B<br/>
|
||||
$T('thisMonth'): $(servers[$server]['amounts'][1])B
|
||||
<!--#end if#-->
|
||||
</div>
|
||||
</div><!-- /section -->
|
||||
</form>
|
||||
<!--#end for#-->
|
||||
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
\$('.showserver').click(function () {
|
||||
\$(this).parent().next().toggle();
|
||||
\$(this).parent().next().next().toggle();
|
||||
if (\$(this).attr("value") == "$T('showDetails')") {
|
||||
\$(this).attr("value", "$T('hideDetails')");
|
||||
} else {
|
||||
\$(this).attr("value", "$T('showDetails')");
|
||||
}
|
||||
});
|
||||
\$('#addServerButton').click(function(){
|
||||
\$('#addServer').hide();
|
||||
\$('#addServerContent').show();
|
||||
});
|
||||
\$('.testServer').click(function(event){
|
||||
\$(this).attr("disabled", "disabled")
|
||||
\$.ajax({
|
||||
type: "POST",
|
||||
url: "../../tapi",
|
||||
data: "mode=config&name=test_server&" + \$(this).parents('form:first').serialize() + "&apikey=" + \$('#apikey').val(),
|
||||
success: function(msg){
|
||||
alert(msg);
|
||||
\$(event.target).removeAttr("disabled")
|
||||
}
|
||||
});
|
||||
});
|
||||
\$('.delServer').click(function(){
|
||||
if( confirm("$T('Plush-confirm')") )
|
||||
\$(this).parents('form:first').attr('action','delServer').submit();
|
||||
return false;
|
||||
});
|
||||
\$('.clrServer').click(function(){
|
||||
if( confirm("$T('Plush-confirm')") )
|
||||
\$(this).parents('form:first').attr('action','clrServer').submit();
|
||||
return false;
|
||||
});
|
||||
\$('.toggleServerCheckbox').click(function(){
|
||||
var whichServer = \$(this).attr("rel");
|
||||
\$.ajax({
|
||||
type: "POST",
|
||||
url: "toggleServer",
|
||||
data: {server: whichServer, session: "$session" }
|
||||
}).done(function() {
|
||||
location.reload();
|
||||
});
|
||||
});
|
||||
});
|
||||
</script>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
543
interfaces/Config/templates/config_sorting.tmpl
Normal file
@@ -0,0 +1,543 @@
|
||||
<!--#set global $pane="Sorting"#-->
|
||||
<!--#set global $help_uri="configure-sorting-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="saveSorting" method="post" name="fullform" id="fullform">
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<input id="complete_dir" type="hidden" value="$complete_dir" />
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('seriesSorting')</h3>
|
||||
<p>
|
||||
<b>$T('affectedCat')</b><br/>
|
||||
<select name="tv_cat" multiple="multiple" class="multiple_cats">
|
||||
<!--#for $ct in $cat_list#-->
|
||||
<option value="$ct" <!--#if $ct in $tv_categories then 'selected="selected"' else ""#--> >$Tspec($ct)</option>
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<h5 class="darkred nomargin">$T('ft-download'): <span class="path">$complete_dir</span></h5>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config wide" for="enable_tv_sorting">$T('opt-tvsort')</label>
|
||||
<input type="checkbox" name="enable_tv_sorting" id="enable_tv_sorting" value="1" <!--#if int($enable_tv_sorting) > 0 then 'checked="checked"' else ""#--> />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="tvfoldername">$T('sortString')</label>
|
||||
<input type="text" id="tvfoldername" name="tv_sort_string" value="$tv_sort_string" size="50" />
|
||||
<input type="button" value="$T('button-clear')" class="clearBtn" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config">$T('presetSort')</label>
|
||||
<div class="presets float-left">
|
||||
<input type="button" onclick="tvSet('%sn/Season %s/%sn - %sx%0e - %en.%ext')" value="$T('button-Season1x05')" />
|
||||
<input type="button" onclick="tvSet('%sn/Season %s/%sn - S%0sE%0e - %en.%ext')" value="$T('button-SeasonS01E05')" /><br/>
|
||||
<input type="button" onclick="tvSet('%sn/%sx%0e - %en/%sn - %sx%0e - %en.%ext')" value="$T('button-Ep1x05')" />
|
||||
<input type="button" onclick="tvSet('%sn/S%0sE%0e - %en/%sn - S%0sE%0e - %en.%ext')" value="$T('button-EpS01E05')" />
|
||||
</div>
|
||||
</div>
|
||||
<div id="previewtv" class="example">
|
||||
<div class="field-pair">
|
||||
<label class="config" for="tvsamplename">Test Data</label>
|
||||
<input type="text" id="tvsamplename" name="tvsamplename" placeholder="$T('show-name') S01E05 - $T('ep-name') [DTS]" size="50" />
|
||||
<input type="button" value="$T('button-clear')" class="clearBtn" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config">$T('sortResult')</label>
|
||||
<span class="desc path" id="previewtv-result"> </span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config">$T('sort-legenda')</label>
|
||||
<input type="button" value="$T('sort-legenda')" onclick="jQuery(this).hide(); jQuery('#Key1').show();" />
|
||||
<table id="Key1" class="Key">
|
||||
<thead>
|
||||
<tr>
|
||||
<th class="align-right">$T('sort-meaning')</th>
|
||||
<th>$T('sort-pattern')</th>
|
||||
<th>$T('sort-result')</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('show-name'):</b></td>
|
||||
<td>%sn</td>
|
||||
<td>$T('show-sp-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%s.n</td>
|
||||
<td>$T('show-dot-name')</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>%s_n</td>
|
||||
<td>$T('show-us-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('show-name'):</b></td>
|
||||
<td>%sN</td>
|
||||
<td>$T('show-sp-name') ($T('case-adjusted'))</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>%s.N</td>
|
||||
<td>$T('show-dot-name') ($T('case-adjusted'))</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%s_N</td>
|
||||
<td>$T('show-us-name') ($T('case-adjusted'))</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('show-seasonNum'):</b></td>
|
||||
<td>%s</td>
|
||||
<td>1</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%0s</td>
|
||||
<td>01</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('show-epNum'):</b></td>
|
||||
<td>%e</td>
|
||||
<td>5</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%0e</td>
|
||||
<td>05</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('ep-name'):</b></td>
|
||||
<td>%en</td>
|
||||
<td>$T('ep-sp-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%e.n</td>
|
||||
<td>$T('ep-dot-name')</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>%e_n</td>
|
||||
<td>$T('ep-us-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('fileExt'):</b></td>
|
||||
<td>%ext</td>
|
||||
<td>avi</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('orgFilename'):</b></td>
|
||||
<td>%fn</td>
|
||||
<td>$T("sort-File")</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('orgDirname'):</b></td>
|
||||
<td>%dn</td>
|
||||
<td>$T("sort-Folder")</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('lowercase'):</b></td>
|
||||
<td>{$T('TEXT')}</td>
|
||||
<td>$T('text')</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('genericSort')</h3>
|
||||
<p>
|
||||
<b>$T('affectedCat')</b><br/>
|
||||
<select name="movie_cat" multiple="multiple" class="multiple_cats">
|
||||
<!--#for $ct in $cat_list#-->
|
||||
<option value="$ct" <!--#if $ct in $movie_categories then 'selected="selected"' else ""#--> >$Tspec($ct)</option>
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<h5 class="darkred nomargin">$T('ft-download'): <span class="path">$complete_dir</span></h5>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config wide" for="enable_movie_sorting">$T('opt-movieSort')</label>
|
||||
<input type="checkbox" name="enable_movie_sorting" id="enable_movie_sorting" value="1" <!--#if int($enable_movie_sorting) > 0 then 'checked="checked"' else ""#--> />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config wide" for="movie_extra_folder">$T('opt-movieExtra')</label>
|
||||
<input type="checkbox" name="movie_extra_folder" id="movie_extra_folder" value="1" <!--#if int($movie_extra_folder) > 0 then 'checked="checked"' else ""#--> />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="moviefoldername">$T('sortString')</label>
|
||||
<input type="text" name="movie_sort_string" id="moviefoldername" value="$movie_sort_string" size="50" />
|
||||
<input type="button" value="$T('button-clear')" class="clearBtn" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="movieextra">$T('multiPartLabel')</label>
|
||||
<input type="text" name="movie_sort_extra" id="movieextra" value="$movie_sort_extra" size="50" />
|
||||
<input type="button" value="$T('button-clear')" class="clearBtn" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config">$T('presetSort')</label>
|
||||
<div class="presets float-left">
|
||||
<input type="button" onclick="movieSet('%title (%y)/%title (%y).%ext',' CD%1');movieExtraFolder(false)" value="$T('button-inFolders')" />
|
||||
<input type="button" onclick="movieSet('%title (%y).%ext',' CD%1');movieExtraFolder(true)" value="$T('button-noFolders')" />
|
||||
<input type="button" onclick="movieSet('%0decade/%title (%y).%ext',' CD%1');movieExtraFolder(true)" value="Decades 1" />
|
||||
</div>
|
||||
</div>
|
||||
<div id="previewmovie" class="example">
|
||||
<div class="field-pair">
|
||||
<label class="config" for="moviesamplename">Test Data</label>
|
||||
<input type="text" id="moviesamplename" name="moviesamplename" placeholder="$T('movie-sp-name') (2009)" size="50" />
|
||||
<input type="button" value="$T('button-clear')" class="clearBtn" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config">$T('sortResult')</label>
|
||||
<span class="desc path" id="previewmovie-result"> </span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config">$T('sort-legenda')</label>
|
||||
<input type="button" value="$T('sort-legenda')" onclick="jQuery(this).hide(); jQuery('#Key2').show();" />
|
||||
<table id="Key2" class="Key">
|
||||
<thead>
|
||||
<tr>
|
||||
<th class="align-right">$T('sort-meaning')</th>
|
||||
<th>$T('sort-pattern')</th>
|
||||
<th>$T('sort-result')</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('sort-title'):</b></td>
|
||||
<td>%title</td>
|
||||
<td>$T('movie-sp-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%.title</td>
|
||||
<td>$T('movie-dot-name')</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>%_title</td>
|
||||
<td>$T('movie-us-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('year'):</b></td>
|
||||
<td>%y</td>
|
||||
<td>2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('extension'):</b></td>
|
||||
<td>%ext</td>
|
||||
<td>avi</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('decade'):</b></td>
|
||||
<td>%decade</td>
|
||||
<td>00</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>%0decade</td>
|
||||
<td>2000</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('orgFilename'):</b></td>
|
||||
<td>%fn</td>
|
||||
<td>$T('sort-File')</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('orgDirname'):</b></td>
|
||||
<td>%dn</td>
|
||||
<td>$T("sort-Folder")</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('lowercase'):</b></td>
|
||||
<td>{$T('TEXT')}</td>
|
||||
<td>$T('text')</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
<tbody>
|
||||
<tr>
|
||||
<th class="align-right"><b>$T('multiPartLabel')</b></th>
|
||||
<th>$T('sort-pattern')</th>
|
||||
<th>$T('sort-result')</th>
|
||||
</tr>
|
||||
</tbody>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('partNumber'):</b></td>
|
||||
<td>%1</td>
|
||||
<td>1</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('dateSorting')</h3>
|
||||
<p>
|
||||
<b>$T('affectedCat')</b><br/>
|
||||
<select name="date_cat" multiple="multiple" class="multiple_cats">
|
||||
<!--#for $ct in $cat_list#-->
|
||||
<option value="$ct" <!--#if $ct in $date_categories then 'selected="selected"' else ""#--> >$Tspec($ct)</option>
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
</p>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<h5 class="darkred nomargin">$T('ft-download'): <span class="path">$complete_dir</span></h5>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config wide" for="enable_date_sorting">$T('opt-dateSort')</label>
|
||||
<input type="checkbox" name="enable_date_sorting" id="enable_date_sorting" value="1" <!--#if int($enable_date_sorting) > 0 then 'checked="checked"' else ""#--> />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="datefoldername">$T('sortString')</label>
|
||||
<input type="text" name="date_sort_string" id="datefoldername" value="$date_sort_string" size="50" />
|
||||
<input type="button" value="$T('button-clear')" class="clearBtn" />
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config">$T('presetSort')</label>
|
||||
<div class="presets float-left">
|
||||
<input type="button" onclick="dateSet('%t/%t - %y-%0m-%0d - %desc.%ext')" value="$T('button-ShowNameF')" />
|
||||
<input type="button" onclick="dateSet('%y-%0m/%t - %y-%0m-%0d - %desc.%ext')" value="$T('button-YMF')" />
|
||||
<input type="button" onclick="dateSet('%y-%0m-%0d/%t - %y-%0m-%0d - %desc.%ext')" value="$T('button-DailyF')" />
|
||||
</div>
|
||||
</div>
|
||||
<div id="previewdate" class="example">
|
||||
<div class="field-pair">
|
||||
<label class="config" for="datesamplename">Test Data</label>
|
||||
<input type="text" id="datesamplename" name="datesamplename" placeholder="$T('show-name') 2009-01-02" size="50" />
|
||||
<input type="button" value="$T('button-clear')" class="clearBtn" />
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config">$T('sortResult')</label>
|
||||
<span class="desc path" id="previewdate-result"> </span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config">$T('sort-legenda')</label>
|
||||
<input type="button" value="$T('sort-legenda')" onclick="jQuery(this).hide(); jQuery('#Key3').show();" />
|
||||
<table id="Key3" class="Key">
|
||||
<thead>
|
||||
<tr>
|
||||
<th class="align-right">$T('sort-meaning')</th>
|
||||
<th>$T('sort-pattern')</th>
|
||||
<th>$T('sort-result')</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('show-name'):</b></td>
|
||||
<td>%t</td>
|
||||
<td>$T('show-sp-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%.t</td>
|
||||
<td>$T('show-dot-name')</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>%_t</td>
|
||||
<td>$T('show-us-name')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('year'):</b></td>
|
||||
<td>%y</td>
|
||||
<td>2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('month'):</b></td>
|
||||
<td>%m</td>
|
||||
<td>1</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%0m</td>
|
||||
<td>01</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('day-of-month'):</b></td>
|
||||
<td>%d</td>
|
||||
<td>2</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%0d</td>
|
||||
<td>02</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('decade'):</b></td>
|
||||
<td>%decade</td>
|
||||
<td>00</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td> </td>
|
||||
<td>%0decade</td>
|
||||
<td>2000</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="align-right"><b>$T('orgFilename'):</b></td>
|
||||
<td>%fn</td>
|
||||
<td>$T('sort-File')</td>
|
||||
</tr>
|
||||
<tr class="even">
|
||||
<td class="align-right"><b>$T('lowercase'):</b></td>
|
||||
<td>{$T('TEXT')}</td>
|
||||
<td>$T('text')</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="padding alt">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</form>
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<script>
|
||||
// http://stackoverflow.com/questions/2219924/idiomatic-jquery-delayed-event-only-after-a-short-pause-in-typing-e-g-timew
|
||||
var typewatch = (function(){
|
||||
var timer = 0;
|
||||
return function(callback, ms){
|
||||
clearTimeout (timer);
|
||||
timer = setTimeout(callback, ms);
|
||||
}
|
||||
})();
|
||||
|
||||
function tvSet(val) {
|
||||
\$('#tvfoldername').val(val);
|
||||
new_previewtv();
|
||||
}
|
||||
|
||||
function movieSet(val, val2) {
|
||||
\$('#moviefoldername').val(val);
|
||||
\$('#movieextra').val(val2);
|
||||
new_previewmovie();
|
||||
}
|
||||
|
||||
function movieExtraFolder(value) {
|
||||
\$('#movie_extra_folder').attr("checked", value);
|
||||
}
|
||||
|
||||
function dateSet(val) {
|
||||
\$('#datefoldername').val(val);
|
||||
new_previewdate();
|
||||
}
|
||||
|
||||
function new_previewtv() {
|
||||
var \$tvsortstring = \$('#tvfoldername').val();
|
||||
if(\$tvsortstring.length > 2) {
|
||||
typewatch(function () {
|
||||
\$('#previewtv').show();
|
||||
\$('#previewtv-result').addClass("loading");
|
||||
\$.ajax({
|
||||
type: "GET",
|
||||
url: "../../tapi",
|
||||
data: {mode:'eval_sort', value: 'series', name: \$('#tvsamplename').val(), title: \$tvsortstring, apikey: '$session', output: 'json' },
|
||||
success: function(data){
|
||||
\$('#previewtv-result').removeClass("loading failure").html(data.result);
|
||||
},
|
||||
error: function(data){ \$('#previewtv-result').removeClass("loading").addClass("failure").html('need more information to process'); }
|
||||
});
|
||||
}, 500);
|
||||
}
|
||||
else
|
||||
\$('#previewtv').hide();
|
||||
}
|
||||
|
||||
function new_previewmovie() {
|
||||
var \$moviesortstring = \$('#moviefoldername').val();
|
||||
if(\$moviesortstring.length > 2) {
|
||||
typewatch(function () {
|
||||
\$('#previewmovie').show();
|
||||
\$('#previewmovie-result').addClass("loading");
|
||||
\$.ajax({
|
||||
type: "GET",
|
||||
url: "../../tapi",
|
||||
data: {mode:'eval_sort', value: 'generic', name: \$('#moviesamplename').val(), title: \$moviesortstring, movieextra: \$('#movieextra').val(), apikey: '$session', output: 'json' },
|
||||
success: function(data){
|
||||
\$('#previewmovie-result').removeClass("loading failure").html(data.result);
|
||||
},
|
||||
error: function(data){ \$('#previewmovie-result').removeClass("loading").addClass("failure").html('need more information to process'); }
|
||||
});
|
||||
}, 500);
|
||||
}
|
||||
else
|
||||
\$('#previewmovie').hide();
|
||||
}
|
||||
|
||||
function new_previewdate() {
|
||||
var \$datesortstring = \$('#datefoldername').val();
|
||||
if(\$datesortstring.length > 2) {
|
||||
typewatch(function () {
|
||||
\$('#previewdate').show();
|
||||
\$('#previewdate-result').addClass("loading");
|
||||
\$.ajax({
|
||||
type: "GET",
|
||||
url: "../../tapi",
|
||||
data: {mode:'eval_sort', value: 'date', name: \$('#datesamplename').val(), title: \$datesortstring, apikey: '$session', output: 'json' },
|
||||
success: function(data){
|
||||
\$('#previewdate-result').removeClass("loading failure").html(data.result);
|
||||
},
|
||||
error: function(data){ \$('#previewdate-result').removeClass("loading").addClass("failure").html('need more information to process'); }
|
||||
});
|
||||
}, 500);
|
||||
}
|
||||
else
|
||||
\$('#previewdate').hide();
|
||||
}
|
||||
|
||||
</script>
|
||||
|
||||
<script>
|
||||
\$(document).ready(function(){
|
||||
new_previewtv();
|
||||
new_previewmovie();
|
||||
new_previewdate();
|
||||
|
||||
\$('#tvfoldername, #tvsamplename').bind("keyup focus", new_previewtv);
|
||||
\$('#moviefoldername, #movieextra, #moviesamplename').bind("keyup focus", new_previewmovie);
|
||||
\$('#datefoldername, #datesamplename').bind("keyup focus", new_previewdate);
|
||||
\$('.clearBtn').click(function(){
|
||||
\$(this).prev().val('').focus();
|
||||
});
|
||||
});
|
||||
</script>
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
59
interfaces/Config/templates/config_special.tmpl
Normal file
@@ -0,0 +1,59 @@
|
||||
<!--#set global $pane="Special"#-->
|
||||
<!--#set global $help_uri="configure+special-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="saveSpecial" method="post" name="fullform" id="fullform">
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<div class="padTable">
|
||||
<h3 class="darkred nomargin">$T('explain-special')</h3>
|
||||
</div>
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('sptag-boolean')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<!--#set $odd = False#-->
|
||||
<!--#for $option in $switches#-->
|
||||
<!--#set $odd = not $odd#-->
|
||||
<div class="field-pair <!--#if $odd then "alt" else ""#-->">
|
||||
<label class="config wide" for="$option[0]">$option[0] ( <span class="path"><!--#if $option[2] then $T('on') else $T('off')#--></span> )</label>
|
||||
<input type="checkbox" name="$option[0]" id="$option[0]" value="1" <!--#if int($option[1]) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc"> </span>
|
||||
</div>
|
||||
<!--#end for#-->
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('sptag-entries')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<!--#set $odd = False#-->
|
||||
<!--#for $option in $entries#-->
|
||||
<!--#set $odd = not $odd#-->
|
||||
<div class="field-pair <!--#if $odd then "alt" else ""#-->">
|
||||
<label class="config narrow" for="$option[0]">$option[0] ( <span class="path">$option[2]</span> )</label>
|
||||
<input type="text" name="$option[0]" id="$option[0]" value="$option[1]" />
|
||||
</div>
|
||||
<!--#end for#-->
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="padding alt">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</form>
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
315
interfaces/Config/templates/config_switches.tmpl
Normal file
@@ -0,0 +1,315 @@
|
||||
<!--#set global $pane="Switches"#-->
|
||||
<!--#set global $help_uri="configure-switches-0-7"#-->
|
||||
<!--#include $webdir + "/_inc_header_uc.tmpl"#-->
|
||||
|
||||
<div class="colmask">
|
||||
<form action="saveSwitches" method="post" name="fullform" id="fullform">
|
||||
<input type="hidden" id="session" name="session" value="$session" />
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('swtag-general')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="check_new_rel">$T('opt-check_new_rel')</label>
|
||||
<select name="check_new_rel" id="check_new_rel">
|
||||
<option value="0" <!--#if $check_new_rel == 0 then 'selected="selected" class="selected"' else ""#--> >$T('off')</option>
|
||||
<option value="1" <!--#if $check_new_rel == 1 then 'selected="selected" class="selected"' else ""#--> >$T('on')</option>
|
||||
<option value="2" <!--#if $check_new_rel == 2 then 'selected="selected" class="selected"' else ""#--> >$T('also-test')</option>
|
||||
</select>
|
||||
<span class="desc">$T('explain-check_new_rel')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="auto_browser">$T('opt-auto_browser')</label>
|
||||
<input type="checkbox" name="auto_browser" id="auto_browser" value="1" <!--#if int($auto_browser) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-auto_browser')</span>
|
||||
</div>
|
||||
<div class="field-pair alt <!--#if not $have_ampm then "disabled" else "" #-->">
|
||||
<label class="config" for="ampm">$T('opt-ampm')</label>
|
||||
<input type="checkbox" name="ampm" id="ampm" value="1" <!--#if int($ampm) > 0 then 'checked="checked"' else ""#--> <!--#if not $have_ampm then 'readonly="readonly" disabled="disabled"' else "" #--> />
|
||||
<span class="desc">$T('explain-ampm')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('swtag-server')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="max_art_tries">$T('opt-max_art_tries')</label>
|
||||
<input type="number" name="max_art_tries" id="max_art_tries" value="$max_art_tries" size="8" min="2" />
|
||||
<span class="desc">$T('explain-max_art_tries')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="max_art_opt">$T('opt-max_art_opt')</label>
|
||||
<input type="checkbox" name="max_art_opt" id="max_art_opt" value="1" <!--#if int($max_art_opt) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-max_art_opt')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="auto_disconnect">$T('opt-auto_disconnect')</label>
|
||||
<input type="checkbox" name="auto_disconnect" id="auto_disconnect" value="1" <!--#if int($auto_disconnect) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-auto_disconnect')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="send_group">$T('opt-send_group')</label>
|
||||
<input type="checkbox" name="send_group" id="send_group" value="1" <!--#if int($send_group) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-send_group')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="ssl_type">$T('opt-ssl_type')</label>
|
||||
<select name="ssl_type" id="ssl_type">
|
||||
<option value="v23" <!--#if $ssl_type == "v23" then 'selected="selected" class="selected"' else ""#--> >V23</option>
|
||||
<option value="v2" <!--#if $ssl_type == "v2" then 'selected="selected" class="selected"' else ""#--> >V2</option>
|
||||
<option value="v3" <!--#if $ssl_type == "v3" then 'selected="selected" class="selected"' else ""#--> >V3</option>
|
||||
</select>
|
||||
<span class="desc">$T('explain-ssl_type')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('swtag-queue')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="fail_hopeless">$T('opt-fail_hopeless')</label>
|
||||
<input type="checkbox" name="fail_hopeless" id="fail_hopeless" value="1" <!--#if int($fail_hopeless) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-fail_hopeless')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="pre_check">$T('opt-pre_check')</label>
|
||||
<input type="checkbox" name="pre_check" id="pre_check" value="1" <!--#if int($pre_check) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-pre_check')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="no_dupes">$T('opt-no_dupes')</label>
|
||||
<select name="no_dupes" id="no_dupes">
|
||||
<option value="0" <!--#if int($no_dupes) == 0 then 'selected="selected" class="selected"' else ""#--> >$T('nodupes-off')</option>
|
||||
<option value="1" <!--#if int($no_dupes) == 1 then 'selected="selected" class="selected"' else ""#--> >$T('nodupes-ignore')</option>
|
||||
<option value="2" <!--#if int($no_dupes) == 2 then 'selected="selected" class="selected"' else ""#--> >$T('nodupes-pause')</option>
|
||||
</select>
|
||||
<span class="desc">$T('explain-no_dupes')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="pause_on_post_processing">$T('opt-pause_on_post_processing')</label>
|
||||
<input type="checkbox" name="pause_on_post_processing" id="pause_on_post_processing" value="1" <!--#if int($pause_on_post_processing) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-pause_on_post_processing')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="pause_on_pwrar">$T('opt-pause_on_pwrar')</label>
|
||||
<select name="pause_on_pwrar" id="pause_on_pwrar">
|
||||
<option value="0" <!--#if int($pause_on_pwrar) == 0 then 'selected="selected" class="selected"' else ""#--> >$T('nodupes-off')</option>
|
||||
<option value="1" <!--#if int($pause_on_pwrar) == 1 then 'selected="selected" class="selected"' else ""#--> >$T('nodupes-pause')</option>
|
||||
<option value="2" <!--#if int($pause_on_pwrar) == 2 then 'selected="selected" class="selected"' else ""#--> >$T('abort')</option>
|
||||
</select>
|
||||
<span class="desc">$T('explain-pause_on_pwrar')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="top_only">$T('opt-top_only')</label>
|
||||
<input type="checkbox" name="top_only" id="top_only" value="1" <!--#if int($top_only) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-top_only')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="auto_sort">$T('opt-auto_sort')</label>
|
||||
<input type="checkbox" name="auto_sort" id="auto_sort" value="1" <!--#if int($auto_sort) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-auto_sort')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="pre_script">$T('opt-pre_script')</label>
|
||||
<select name="pre_script" id="pre_script">
|
||||
<!--#for $sc in $script_list#-->
|
||||
<!--#if $sc.lower() == $pre_script.lower()#-->
|
||||
<option value="$sc" selected="selected" class="selected">$Tspec($sc)</option>
|
||||
<!--#else#-->
|
||||
<option value="$sc">$Tspec($sc)</option>
|
||||
<!--#end if#-->
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
<span class="desc">$T('explain-pre_script')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('swtag-pp')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="ignore_samples">$T('opt-ignore_samples')</label>
|
||||
<select name="ignore_samples" id="ignore_samples">
|
||||
<option value="0" <!--#if int($ignore_samples) == 0 then 'selected="selected" class="selected"' else ""#--> >$T('igsam-off')</option>
|
||||
<option value="1" <!--#if int($ignore_samples) == 1 then 'selected="selected" class="selected"' else ""#--> >$T('igsam-del')</option>
|
||||
<option value="2" <!--#if int($ignore_samples) == 2 then 'selected="selected" class="selected"' else ""#--> >$T('igsam-not')</option>
|
||||
</select>
|
||||
<span class="desc">$T('explain-ignore_samples')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="quick_check">$T('opt-quick_check')</label>
|
||||
<input type="checkbox" name="quick_check" id="quick_check" value="1" <!--#if int($quick_check) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-quick_check')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="enable_unrar">$T('opt-enable_unrar')</label>
|
||||
<input type="checkbox" name="enable_unrar" id="enable_unrar" value="1" <!--#if int($enable_unrar) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-enable_unrar')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="enable_unzip">$T('opt-enable_unzip')</label>
|
||||
<input type="checkbox" name="enable_unzip" id="enable_unzip" value="1" <!--#if int($enable_unzip) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-enable_unzip')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="enable_filejoin">$T('opt-enable_filejoin')</label>
|
||||
<input type="checkbox" name="enable_filejoin" id="enable_filejoin" value="1" <!--#if int($enable_filejoin) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-enable_filejoin')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="enable_tsjoin">$T('opt-enable_tsjoin')</label>
|
||||
<input type="checkbox" name="enable_tsjoin" id="enable_tsjoin" value="1" <!--#if int($enable_tsjoin) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-ts_join')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="enable_par_cleanup">$T('opt-enable_par_cleanup')</label>
|
||||
<input type="checkbox" name="enable_par_cleanup" id="enable_par_cleanup" value="1" <!--#if int($enable_par_cleanup) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-enable_par_cleanup')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="fail_on_crc">$T('opt-fail_on_crc')</label>
|
||||
<input type="checkbox" name="fail_on_crc" id="fail_on_crc" value="1" <!--#if int($fail_on_crc) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-fail_on_crc')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="safe_postproc">$T('opt-safe_postproc')</label>
|
||||
<input type="checkbox" name="safe_postproc" id="safe_postproc" value="1" <!--#if int($safe_postproc) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-safe_postproc')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="sfv_check">$T('opt-sfv_check')</label>
|
||||
<input type="checkbox" name="sfv_check" id="sfv_check" value="1" <!--#if int($sfv_check) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-sfv_check')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="unpack_check">$T('opt-unpack_check')</label>
|
||||
<input type="checkbox" name="unpack_check" id="unpack_check" value="1" <!--#if int($unpack_check) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-unpack_check')</span>
|
||||
</div>
|
||||
<div class="field-pair <!--#if not $nt then "disabled" else "" #-->">
|
||||
<label class="config" for="par2_multicore">$T('opt-par2_multicore')</label>
|
||||
<input type="checkbox" name="par2_multicore" id="par2_multicore" value="1" <!--#if int($par2_multicore) > 0 then 'checked="checked"' else ""#--> <!--#if not $nt then 'readonly="readonly" disabled="disabled"' else "" #--> />
|
||||
<span class="desc">$T('explain-par2_multicore')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="par_option">$T('opt-par_option')</label>
|
||||
<input type="text" name="par_option" id="par_option" value="$par_option" size="20" />
|
||||
<span class="desc">$T('explain-par_option')</span>
|
||||
</div>
|
||||
<div class="field-pair <!--#if not $have_nice then "disabled" else "" #-->">
|
||||
<label class="config" for="nice">$T('opt-nice')</label>
|
||||
<input type="text" name="nice" id="nice" value="$nice" size="20" <!--#if not $have_nice then 'readonly="readonly" disabled="disabled"' else "" #--> />
|
||||
<span class="desc">$T('explain-nice')</span>
|
||||
</div>
|
||||
<div class="field-pair alt <!--#if not $have_ionice then "disabled" else "" #-->">
|
||||
<label class="config" for="ionice">$T('opt-ionice')</label>
|
||||
<input type="text" name="ionice" id="ionice" value="$ionice" size="20" <!--#if not $have_ionice then 'readonly="readonly" disabled="disabled"' else "" #--> />
|
||||
<span class="desc">$T('explain-ionice')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('swtag-naming')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="folder_rename">$T('opt-folder_rename')</label>
|
||||
<input type="checkbox" name="folder_rename" id="folder_rename" value="1" <!--#if int($folder_rename) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-folder_rename')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="replace_spaces">$T('opt-replace_spaces')</label>
|
||||
<input type="checkbox" name="replace_spaces" id="replace_spaces" value="1" <!--#if int($replace_spaces) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-replace_spaces')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="replace_dots">$T('opt-replace_dots')</label>
|
||||
<input type="checkbox" name="replace_dots" id="replace_dots" value="1" <!--#if int($replace_dots) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-replace_dots')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="replace_illegal">$T('opt-replace_illegal')</label>
|
||||
<input type="checkbox" name="replace_illegal" id="replace_illegal" value="1" <!--#if int($replace_illegal) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-replace_illegal')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="section">
|
||||
<div class="col2">
|
||||
<h3>$T('swtag-quota')</h3>
|
||||
</div><!-- /col2 -->
|
||||
<div class="col1">
|
||||
<fieldset>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="quota_size">$T('opt-quota_size')</label>
|
||||
<input type="text" name="quota_size" id="quota_size" value="$quota_size" size="8" />
|
||||
<span class="desc">$T('explain-quota_size')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="quota_period">$T('opt-quota_period')</label>
|
||||
<select name="quota_period" id="quota_period">
|
||||
<option value="d" <!--#if $quota_period == "d" then 'selected="selected" class="selected"' else ""#--> >$T('day').capitalize()</option>
|
||||
<option value="w" <!--#if $quota_period == "w" then 'selected="selected" class="selected"' else ""#--> >$T('week').capitalize()</option>
|
||||
<option value="m" <!--#if $quota_period == "m" then 'selected="selected" class="selected"' else ""#--> >$T('month').capitalize()</option>
|
||||
<option value="x" <!--#if $quota_period == "x" then 'selected="selected" class="selected"' else ""#--> >$T('manual').capitalize()</option>
|
||||
</select>
|
||||
<span class="desc">$T('explain-quota_period')</span>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="config" for="quota_day">$T('opt-quota_day')</label>
|
||||
<input type="text" name="quota_day" id="quota_day" value="$quota_day" size="20" />
|
||||
<span class="desc">$T('explain-quota_day')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="config" for="quota_resume">$T('opt-quota_resume')</label>
|
||||
<input type="checkbox" name="quota_resume" id="quota_resume" value="1" <!--#if int($quota_resume) > 0 then 'checked="checked"' else ""#--> />
|
||||
<span class="desc">$T('explain-quota_resume')</span>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /col1 -->
|
||||
</div><!-- /section -->
|
||||
<div class="padding alt">
|
||||
<input type="submit" value="$T('button-saveChanges')" class="saveButton" />
|
||||
<input type="button" value="$T('button-restart') SABnzbd" class="sabnzbd_restart" />
|
||||
</div>
|
||||
</form>
|
||||
</div><!-- /colmask -->
|
||||
|
||||
<!--#include $webdir + "/_inc_footer_uc.tmpl"#-->
|
||||
2
interfaces/Config/templates/main.tmpl
Normal file
@@ -0,0 +1,2 @@
|
||||
/* This file was intentionally left blank and is only needed for 'skin' detection routine */
|
||||
/* https://github.com/thezoggy/sabnzbd-uni_Config */
|
||||
|
After Width: | Height: | Size: 180 B |
|
After Width: | Height: | Size: 180 B |
|
After Width: | Height: | Size: 178 B |
|
After Width: | Height: | Size: 120 B |
|
After Width: | Height: | Size: 119 B |
|
After Width: | Height: | Size: 141 B |
|
After Width: | Height: | Size: 96 B |
|
After Width: | Height: | Size: 128 B |
|
After Width: | Height: | Size: 137 B |
|
After Width: | Height: | Size: 4.3 KiB |
|
After Width: | Height: | Size: 4.3 KiB |
|
After Width: | Height: | Size: 5.2 KiB |
|
After Width: | Height: | Size: 4.3 KiB |
15
interfaces/Config/templates/staticcfg/css/style.css
Normal file
|
After Width: | Height: | Size: 15 KiB |
|
After Width: | Height: | Size: 20 KiB |
|
After Width: | Height: | Size: 5.5 KiB |
|
After Width: | Height: | Size: 7.7 KiB |
|
After Width: | Height: | Size: 5.5 KiB |
BIN
interfaces/Config/templates/staticcfg/ico/favicon.ico
Normal file
|
After Width: | Height: | Size: 1.1 KiB |
BIN
interfaces/Config/templates/staticcfg/images/button.png
Normal file
|
After Width: | Height: | Size: 85 B |
BIN
interfaces/Config/templates/staticcfg/images/loading-bar.gif
Normal file
|
After Width: | Height: | Size: 11 KiB |
BIN
interfaces/Config/templates/staticcfg/images/loading16.gif
Normal file
|
After Width: | Height: | Size: 1.1 KiB |
BIN
interfaces/Config/templates/staticcfg/images/logo.png
Normal file
|
After Width: | Height: | Size: 2.8 KiB |
BIN
interfaces/Config/templates/staticcfg/images/mini-left.gif
Normal file
|
After Width: | Height: | Size: 871 B |
BIN
interfaces/Config/templates/staticcfg/images/mini-right.gif
Normal file
|
After Width: | Height: | Size: 872 B |
BIN
interfaces/Config/templates/staticcfg/images/no16.png
Normal file
|
After Width: | Height: | Size: 1.0 KiB |
BIN
interfaces/Config/templates/staticcfg/images/select_arrow.gif
Normal file
|
After Width: | Height: | Size: 52 B |
BIN
interfaces/Config/templates/staticcfg/images/yes16.png
Normal file
|
After Width: | Height: | Size: 828 B |
207
interfaces/Config/templates/staticcfg/js/script.js
Normal file
@@ -9,7 +9,7 @@
|
||||
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
|
||||
<html>
|
||||
<head>
|
||||
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||
<title>SABnzbd $version - $T('queued'): $mbleft $T('MB')</title>
|
||||
<link rel="alternate" type="application/rss+xml" title="RSS 2.0" href="${path}rss?mode=history"/>
|
||||
|
||||
@@ -126,8 +126,10 @@
|
||||
<div class="config_sprite_container sprite_config_nav_scheduling">$T('Plush-cmenu-scheduling')</div></a></li>
|
||||
<li><a class="#if $pane=="Email"#nav_active#end if#" id="config_nav_email" href="${path}config/notify/">
|
||||
<div class="config_sprite_container sprite_config_nav_email">$T('cmenu-notif')</div></a></li>
|
||||
<!--#if 0#-->
|
||||
<li><a class="#if $pane=="Index Sites"#nav_active#end if#" id="config_nav_index_sites" href="${path}config/indexers/">
|
||||
<div class="config_sprite_container sprite_config_nav_indexsites">$T('cmenu-newzbin')</div></a></li>
|
||||
<!--#end if#-->
|
||||
<li><a class="#if $pane=="Categories"#nav_active#end if#" id="config_nav_categories" href="${path}config/categories/">
|
||||
<div class="config_sprite_container sprite_config_nav_categories">$T('cmenu-cat')</div></a></li>
|
||||
<li><a class="#if $pane=="Sorting"#nav_active#end if#" id="config_nav_sorting" href="${path}config/sorting/">
|
||||
|
||||
@@ -10,7 +10,7 @@
|
||||
</table>
|
||||
<div class="sabnzbd_logo main_sprite_container sprite_sabnzbdplus_logo"></div>
|
||||
<p><strong>SABnzbd $T('version'):</strong> $version</p>
|
||||
<p><small>Copyright (C) 2008-2012, The SABnzbd Team <<a href="mailto:team@sabnzbd.org">team@sabnzbd.org</a>></small></p>
|
||||
<p><small>Copyright (C) 2008-2012, The SABnzbd Team <team@sabnzbd.org></small></p>
|
||||
<p><small>$T('yourRights')</small></p>
|
||||
</div>
|
||||
|
||||
|
||||
@@ -43,90 +43,6 @@
|
||||
</fieldset>
|
||||
</div><!-- /component-group1 -->
|
||||
|
||||
<div id="core-component-group2" class="component-group clearfix">
|
||||
<div class="component-group-desc">
|
||||
<h3>Newzbin $T('accountInfo')</h3>
|
||||
<p>$T('explain-newzbin')</p>
|
||||
</div>
|
||||
<fieldset class="component-group-list">
|
||||
<div class="field-pair">
|
||||
<label class="nocheck clearfix" for="username_newzbin">
|
||||
<span class="component-title">$T('opt-username_newzbin')</span>
|
||||
<input type="text" name="username_newzbin" id="username_newzbin" value="$username_newzbin"/>
|
||||
</label>
|
||||
<label class="nocheck clearfix">
|
||||
<span class="component-title"> </span>
|
||||
<span class="component-desc">$T('explain-username_newzbin')</span>
|
||||
</label>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="nocheck clearfix" for="password_newzbin">
|
||||
<span class="component-title">$T('opt-password_newzbin')</span>
|
||||
<input type="password" name="password_newzbin" id="password_newzbin" value="$password_newzbin"/>
|
||||
</label>
|
||||
<label class="nocheck clearfix">
|
||||
<span class="component-title"> </span>
|
||||
<span class="component-desc">$T('explain-password_newzbin')</span>
|
||||
</label>
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /component-group2 -->
|
||||
|
||||
<div id="core-component-group3" class="component-group clearfix">
|
||||
<div class="component-group-desc">
|
||||
<h3>Newzbin $T('newzbinBookmarks')</h3>
|
||||
<p>
|
||||
<input type="button" class="juiButton" id="getBookmarks" value="$T('link-getBookmarks')" />
|
||||
<br/><br/>
|
||||
<!--#if $bookmarks_list#-->
|
||||
<input type="button" class="juiButton" id="hideBookmarks" value="$T('link-HideBM')" />
|
||||
<!--#else#-->
|
||||
<input type="button" class="juiButton" id="showBookmarks" value="$T('link-ShowBM')" />
|
||||
<!--#end if#-->
|
||||
</p>
|
||||
</div>
|
||||
<fieldset class="component-group-list">
|
||||
<div class="field-pair">
|
||||
<input type="checkbox" name="newzbin_bookmarks" id="newzbin_bookmarks" value="1" <!--#if $newzbin_bookmarks > 0 then "checked=1" else ""#--> />
|
||||
<label class="clearfix" for="newzbin_bookmarks">
|
||||
<span class="component-title">$T('opt-newzbin_bookmarks')</span>
|
||||
<span class="component-desc">$T('explain-newzbin_bookmarks')</span>
|
||||
</label>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<input type="checkbox" name="newzbin_unbookmark" id="newzbin_unbookmark" value="1" <!--#if $newzbin_unbookmark > 0 then "checked=1" else ""#--> />
|
||||
<label class="clearfix" for="newzbin_unbookmark">
|
||||
<span class="component-title">$T('opt-newzbin_unbookmark')</span>
|
||||
<span class="component-desc">$T('explain-newzbin_unbookmark')</span>
|
||||
</label>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
<label class="nocheck clearfix" for="bookmark_rate">
|
||||
<span class="component-title">$T('opt-bookmark_rate')</span>
|
||||
<input type="text" name="bookmark_rate" id="bookmark_rate" size="6" value="$bookmark_rate"/>
|
||||
</label>
|
||||
<label class="nocheck clearfix">
|
||||
<span class="component-title"> </span>
|
||||
<span class="component-desc">$T('explain-bookmark_rate')</span>
|
||||
</label>
|
||||
</div>
|
||||
</fieldset>
|
||||
</div><!-- /component-group3 -->
|
||||
|
||||
<!--#if $bookmarks_list#-->
|
||||
<div id="core-component-group4" class="component-group clearfix">
|
||||
<div class="component-group-desc">
|
||||
<h3>Newzbin $T('accountInfo')</h3>
|
||||
<p>$T('explain-newzbin')</p>
|
||||
</div>
|
||||
<fieldset class="component-group-list">
|
||||
<!--#for $msgid in $bookmarks_list#-->
|
||||
<a href="https://$newzbin_url/browse/post/$msgid/" target="_blank">$msgid</a><br/>
|
||||
<!--#end for#-->
|
||||
</fieldset>
|
||||
</div><!-- /component-group4 -->
|
||||
<!--#end if#-->
|
||||
|
||||
<div class="component-group-last clearfix">
|
||||
<div class="component-group-desc">
|
||||
<h3> </h3>
|
||||
|
||||
@@ -174,6 +174,7 @@ $T('explain-RSS')
|
||||
<table class="rssTable">
|
||||
<tr>
|
||||
<th>$T('Plush-rss-delete')</th>
|
||||
<th> </th>
|
||||
<th>$T('rss-order')</th>
|
||||
<th>$T('rss-type')</th>
|
||||
<th>$T('rss-filter')</th>
|
||||
@@ -187,6 +188,7 @@ $T('explain-RSS')
|
||||
<form action="upd_rss_filter" method="get">
|
||||
<tr class="odd">
|
||||
<td></td>
|
||||
<td><input type="checkbox" name="enabled" value="1" checked="checked" /></td>
|
||||
<td></td>
|
||||
<td>
|
||||
<select name="filter_type">
|
||||
@@ -255,7 +257,10 @@ $T('explain-RSS')
|
||||
</td>
|
||||
|
||||
<form action="upd_rss_filter" method="get">
|
||||
<td>
|
||||
<td>
|
||||
<input type="checkbox" name="enabled" value="1" <!--#if $filter[6] == '1' then 'checked="checked"' else ""#--> />
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" size="3" name="new_index" value=$fnum>
|
||||
</td>
|
||||
<td>
|
||||
@@ -310,6 +315,7 @@ $T('explain-RSS')
|
||||
<input type="hidden" name="feed" value="$feed"/>
|
||||
<input type="hidden" name="session" value="$session">
|
||||
<input type="submit" class="juiButton" value="$T('button-save')"/>
|
||||
<!--#if not $rss[$feed].filter_states[$fnum]#--> $T('Incorrect filter')<!--#end if#-->
|
||||
</td>
|
||||
</form>
|
||||
</tr>
|
||||
|
||||
@@ -36,18 +36,15 @@ else:
|
||||
</label>
|
||||
</div>
|
||||
<div class="field-pair alt">
|
||||
<label class="nocheck clearfix" for="dayofweek">
|
||||
<label class="nocheck clearfix" for="daysofweek">
|
||||
<span class="component-title">$T('sch-frequency')</span>
|
||||
<select name="dayofweek" id="dayofweek">
|
||||
<option value="*" selected>$T('daily')</option>
|
||||
<option value="1">$T('monday')</option>
|
||||
<option value="2">$T('tuesday')</option>
|
||||
<option value="3">$T('wednesday')</option>
|
||||
<option value="4">$T('thursday')</option>
|
||||
<option value="5">$T('friday')</option>
|
||||
<option value="6">$T('saturday')</option>
|
||||
<option value="7">$T('sunday')</option>
|
||||
</select>
|
||||
<input type="checkbox" name="daysofweek" value="1">$T('monday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="2">$T('tuesday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="3">$T('wednesday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="4">$T('thursday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="5">$T('friday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="6">$T('saturday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="7">$T('sunday')<br/>
|
||||
</label>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
|
||||
@@ -46,7 +46,7 @@
|
||||
<div class="field-pair alt">
|
||||
<label class="nocheck clearfix" for="password">
|
||||
<span class="component-title">$T('srv-password')</span>
|
||||
<input type="text" size="25" name="password"/>
|
||||
<input type="password" size="25" name="password"/>
|
||||
</label>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
@@ -156,7 +156,7 @@
|
||||
<div class="field-pair alt">
|
||||
<label class="nocheck clearfix" for="password">
|
||||
<span class="component-title">$T('srv-password')</span>
|
||||
<input type="text" size="25" name="password" value="$servers[$server]['password']" />
|
||||
<input type="password" size="25" name="password" value="$servers[$server]['password']" />
|
||||
</label>
|
||||
</div>
|
||||
<div class="field-pair">
|
||||
|
||||
@@ -26,7 +26,6 @@
|
||||
<a class="sf-with-ul">$T('menu-queue')</a>
|
||||
<ul>
|
||||
<!--#if $have_quota#--><li><a id="reset_quota_now" class="pointer">$T('link-resetQuota')</a></li><!--#end if#-->
|
||||
<!--#if $varExists('newzbinDetails')#--><li><a id="get_bookmarks_now" class="pointer">$T('link-getBookmarks')</a></li><!--#end if#-->
|
||||
<!--#if $have_rss_defined#--><li><a id="get_rss_now" class="pointer">$T('button-rssNow')</a></li><!--#end if#-->
|
||||
<!--#if $have_watched_dir#--><li><a id="get_watched_now" class="pointer">$T('sch-scan_folder')</a></li><!--#end if#-->
|
||||
<li><a id="topmenu_toggle" class="pointer">$T('Plush-topMenu')</a></li>
|
||||
|
||||
@@ -56,7 +56,7 @@
|
||||
</td>
|
||||
|
||||
<td class="download-title">
|
||||
<a href="nzb/$slot.nzo_id/" title="$T('status'): $T('post-'+$slot.status)<br/>$T('nzo-age'): $slot.avg_age<br/><!--#if $slot.missing#-->$T('missingArt'): $slot.missing<!--#end if#-->">$slot.filename</a>
|
||||
<a href="nzb/$slot.nzo_id/" title="$T('status'): $T('post-'+$slot.status)<br/>$T('nzo-age'): $slot.avg_age<br/><!--#if $slot.missing#-->$T('missingArt'): $slot.missing<!--#end if#-->">$slot.filename.replace('.', '.​').replace('_', '_​')</a>
|
||||
</td>
|
||||
|
||||
<td>
|
||||
|
||||
@@ -40,6 +40,7 @@ jQuery(function($){
|
||||
$('#addID').click(function(){ // also works when hitting enter because of <form>
|
||||
if ($('#addID_input').val()!='URL') {
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {
|
||||
@@ -118,15 +119,19 @@ jQuery(function($){
|
||||
|
||||
// fix for touch devices -- toggle visibility
|
||||
$('.sprite_q_menu_pausefor').bind('touchend', function(e) {
|
||||
e.preventDefault();
|
||||
if( $(this).hasClass('sprite_q_menu_pauseforsfHover') ) {
|
||||
$(this).find("ul").toggle();
|
||||
if (! $.browser.safari) {
|
||||
e.preventDefault();
|
||||
if( $(this).hasClass('sprite_q_menu_pauseforsfHover') ) {
|
||||
$(this).find("ul").toggle();
|
||||
}
|
||||
}
|
||||
});
|
||||
$('.sprite_q_queue').bind('touchend', function(e) {
|
||||
e.preventDefault();
|
||||
if( $(this).hasClass('sprite_q_queuesfHover') ) {
|
||||
$(this).find("ul").toggle();
|
||||
if (! $.browser.safari) {
|
||||
e.preventDefault();
|
||||
if( $(this).hasClass('sprite_q_queuesfHover') ) {
|
||||
$(this).find("ul").toggle();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
@@ -154,6 +159,7 @@ jQuery(function($){
|
||||
else
|
||||
$('#speed-wrapper .sprite_q_menu_pausefor').removeClass('sprite_q_menu_pausefor_on');
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'config', name:'set_speedlimit', value: str, apikey: $.plush.apikey}
|
||||
@@ -209,6 +215,7 @@ jQuery(function($){
|
||||
else
|
||||
$('.sprite_q_queue').removeClass('sprite_q_queue_on');
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:'change_complete_action', value: $(this).val(), apikey: $.plush.apikey}
|
||||
@@ -230,6 +237,7 @@ jQuery(function($){
|
||||
value="all";
|
||||
}
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:'delete', value:value, del_files:del_files, apikey: $.plush.apikey},
|
||||
@@ -254,6 +262,7 @@ jQuery(function($){
|
||||
case 'sortSizeDesc': sort='size'; dir='desc'; break;
|
||||
}
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:'sort', sort: sort, dir: dir, apikey: $.plush.apikey},
|
||||
@@ -268,6 +277,7 @@ jQuery(function($){
|
||||
minutes = prompt($(event.target).attr('title'));
|
||||
$.plush.SetQueuePauseInfo(true,minutes+':00');
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'config', name:'set_pause', value: minutes, apikey: $.plush.apikey},
|
||||
@@ -278,6 +288,7 @@ jQuery(function($){
|
||||
// Get Bookmarks
|
||||
$('#get_bookmarks_now').click(function() {
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'newzbin', name:'get_bookmarks', apikey: $.plush.apikey},
|
||||
@@ -288,6 +299,7 @@ jQuery(function($){
|
||||
// Reset Quota
|
||||
$('#reset_quota_now').click(function() {
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'reset_quota', apikey: $.plush.apikey},
|
||||
@@ -298,6 +310,7 @@ jQuery(function($){
|
||||
// Get RSS
|
||||
$('#get_rss_now').click(function() {
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'rss_now', apikey: $.plush.apikey},
|
||||
@@ -308,6 +321,7 @@ jQuery(function($){
|
||||
// Get Watched folder
|
||||
$('#get_watched_now').click(function() {
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'watched_now', apikey: $.plush.apikey},
|
||||
@@ -471,6 +485,7 @@ jQuery(function($){
|
||||
$('#pause_resume').removeClass('sprite_q_pause_on').addClass('sprite_q_pause');
|
||||
$('#pause_int').html("");
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'resume', apikey: $.plush.apikey}
|
||||
@@ -479,6 +494,7 @@ jQuery(function($){
|
||||
$('#pause_resume').removeClass('sprite_q_pause').addClass('sprite_q_pause_on');
|
||||
$('#pause_int').html("");
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'pause', apikey: $.plush.apikey}
|
||||
@@ -522,6 +538,7 @@ jQuery(function($){
|
||||
if ($(this).hasClass('sprite_ql_grip_resume_on')) {
|
||||
$(this).toggleClass('sprite_ql_grip_resume_on').toggleClass('sprite_ql_grip_pause_on');
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:'pause', value: pid, apikey: $.plush.apikey}
|
||||
@@ -529,6 +546,7 @@ jQuery(function($){
|
||||
} else {
|
||||
$(this).toggleClass('sprite_ql_grip_resume_on').toggleClass('sprite_ql_grip_pause_on');
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:'resume', value: pid, apikey: $.plush.apikey}
|
||||
@@ -573,6 +591,7 @@ jQuery(function($){
|
||||
var nzbid = $(this).parent().parent().attr('id');
|
||||
var oldPos = $('#'+nzbid)[0].rowIndex + $.plush.queuecurpage * $.plush.queuePerPage;
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:'priority', value: nzbid, value2: $(this).val(), apikey: $.plush.apikey},
|
||||
@@ -595,6 +614,7 @@ jQuery(function($){
|
||||
var val = $(this).parent().parent().attr('id');
|
||||
var cval = $(this).attr('class').split(" ")[0]; // ignore added "hovering" class
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode: cval, value: val, value2: $(this).val(), apikey: $.plush.apikey},
|
||||
@@ -683,6 +703,7 @@ $.plush.queueprevslots = $.plush.queuenoofslots; // for the next refresh
|
||||
if (table.tBodies[0].rows[i].id == row.id) {
|
||||
val2 = (i + $.plush.queuecurpage * $.plush.queuePerPage);
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'switch', value: row.id, value2: val2, apikey: $.plush.apikey},
|
||||
@@ -768,6 +789,7 @@ $("a","#multiops_inputs").click(function(e){
|
||||
|
||||
if ($('#multi_status').val())
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:$('#multi_status').val(), value: nzo_ids, apikey: $.plush.apikey}
|
||||
@@ -775,6 +797,7 @@ $("a","#multiops_inputs").click(function(e){
|
||||
|
||||
if ($('#multi_cat').val())
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode: 'change_cat', value: nzo_ids, value2: $('#multi_cat').val(), apikey: $.plush.apikey}
|
||||
@@ -782,6 +805,7 @@ $("a","#multiops_inputs").click(function(e){
|
||||
|
||||
if ($('#multi_priority').val())
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'queue', name:'priority', value: nzo_ids, value2: $('#multi_priority').val(), apikey: $.plush.apikey}
|
||||
@@ -789,6 +813,7 @@ $("a","#multiops_inputs").click(function(e){
|
||||
|
||||
if ($('#multi_pp').val())
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode: 'change_opts', value: nzo_ids, value2: $('#multi_pp').val(), apikey: $.plush.apikey}
|
||||
@@ -796,6 +821,7 @@ $("a","#multiops_inputs").click(function(e){
|
||||
|
||||
if ($('#multi_script').val())
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode: 'change_script', value: nzo_ids, value2: $('#multi_script').val(), apikey: $.plush.apikey}
|
||||
@@ -866,9 +892,10 @@ $("a","#multiops_inputs").click(function(e){
|
||||
value="failed";
|
||||
}
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:'history', name:'delete', value:value, del_files:del_files, apikey: $.plush.apikey},
|
||||
data: {mode:'history', name:'delete', value:value, del_files:del_files, search: $('#historySearchBox').val(), apikey: $.plush.apikey},
|
||||
success: function(){
|
||||
$.colorbox.close();
|
||||
$.plush.modalOpen=false;
|
||||
@@ -955,6 +982,7 @@ $("a","#multiops_inputs").click(function(e){
|
||||
$.plush.pendingHistoryRefresh = true;
|
||||
$.colorbox.close();
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "tapi",
|
||||
data: {mode:mode, name:'delete', value: delid, del_files: del_files, apikey: $.plush.apikey},
|
||||
@@ -1081,6 +1109,7 @@ $.plush.histprevslots = $.plush.histnoofslots; // for the next refresh
|
||||
|
||||
// Fetch updated content from queue.tmpl
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "queue/",
|
||||
data: {start: ( page * $.plush.queuePerPage ), limit: $.plush.queuePerPage},
|
||||
@@ -1136,6 +1165,7 @@ $.plush.histprevslots = $.plush.histnoofslots; // for the next refresh
|
||||
|
||||
|
||||
$.ajax({
|
||||
headers: {"Cache-Control": "no-cache"},
|
||||
type: "POST",
|
||||
url: "history/",
|
||||
data: data,
|
||||
@@ -1212,12 +1242,16 @@ $.plush.histprevslots = $.plush.histnoofslots; // for the next refresh
|
||||
SetQueueETAStats : function(speed,kbpersec,timeleft,eta) {
|
||||
|
||||
// ETA/speed stats at top of queue
|
||||
if (kbpersec < 1 && $.plush.paused)
|
||||
if (kbpersec < 1 || $.plush.paused) {
|
||||
$('#stats_eta').html('—');
|
||||
else
|
||||
$('#stats_speed').html('—');
|
||||
$('#time-left').attr('title','—'); // Tooltip on "time left"
|
||||
}
|
||||
else {
|
||||
$('#stats_eta').html(timeleft);
|
||||
$('#stats_speed').html(speed+"B/s");
|
||||
$('#time-left').attr('title',eta); // Tooltip on "time left"
|
||||
$('#stats_speed').html(speed+"B/s");
|
||||
$('#time-left').attr('title',eta); // Tooltip on "time left"
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
<!--#for $warn in $warnings#-->
|
||||
<!--#set $odd = not $odd#-->
|
||||
<tr class="<!--#if $odd then "odd" else "even"#-->">
|
||||
<td>$warn.replace("\n","</td><td>")</td></tr>
|
||||
<td>$warn.replace("\n","</td><td>", 2)</td></tr>
|
||||
<!--#end for#-->
|
||||
</table>
|
||||
<!--#else#-->
|
||||
|
||||
@@ -1,69 +1,4 @@
|
||||
<a href="${helpuri}Configure+Indexers-0-7" id="help" target="_blank">$T('menu-help')</a><h3>Newzbin</h3>
|
||||
<form id="configNewzbin" class="cmxform" autocomplete="off">
|
||||
|
||||
$T('explain-newzbin')<br/>
|
||||
<br/>
|
||||
<div class="EntryBlock">
|
||||
|
||||
|
||||
<fieldset class="EntryFieldSet">
|
||||
<legend>$T('accountInfo')</legend>
|
||||
<hr />
|
||||
<label class="label">$T('opt-username_newzbin'):</label>
|
||||
<input type="text" name="username_newzbin" value="$username_newzbin">
|
||||
<span class="tips">$T('explain-username_newzbin')</span>
|
||||
<br class="clear" />
|
||||
|
||||
|
||||
<label class="label">$T('opt-password_newzbin'):</label>
|
||||
<input type="password" name="password_newzbin" value="$password_newzbin">
|
||||
<span class="tips">$T('explain-password_newzbin')</span>
|
||||
<br class="clear" />
|
||||
</fieldset>
|
||||
|
||||
|
||||
<fieldset class="EntryFieldSet">
|
||||
<legend>$T('newzbinBookmarks')</legend>
|
||||
<hr />
|
||||
|
||||
<label><span class="label">$T('newzbinBookmarks'):</span>
|
||||
<input class="radio" type="checkbox" name="newzbin_bookmarks" value="1" <!--#if $newzbin_bookmarks > 0 then "checked=1" else ""#--> />
|
||||
<span class="tips">$T('explain-newzbin_bookmarks')</span></label>
|
||||
<br class="clear" />
|
||||
|
||||
<label><span class="label">$T('opt-newzbin_unbookmark'):</span>
|
||||
<input class="radio" type="checkbox" name="newzbin_unbookmark" value="1" <!--#if $newzbin_unbookmark > 0 then "checked=1" else ""#--> />
|
||||
<span class="tips">$T('explain-newzbin_unbookmark')</span></label>
|
||||
<br class="clear" />
|
||||
|
||||
<label class="label">$T('opt-bookmark_rate'):</label>
|
||||
<input type="text" name="bookmark_rate" value="$bookmark_rate">
|
||||
<span class="tips">$T('explain-bookmark_rate')</span>
|
||||
<br class="clear" />
|
||||
</fieldset>
|
||||
|
||||
<a class="config" onClick="getBookmarks();">$T('link-getBookmarks')</a>
|
||||
<!--#if $bookmarks_list#-->
|
||||
<a class="config" onClick="lr('config/indexers/hideBookmarks');">$T('link-HideBM')</a>
|
||||
<!--#else#-->
|
||||
<a class="config" onClick="lr('config/indexers/showBookmarks');">$T('link-ShowBM')</a>
|
||||
<!--#end if#-->
|
||||
|
||||
<!--#if $bookmarks_list#-->
|
||||
<fieldset class="EntryFieldSet">
|
||||
<legend>$T('processedBM')</legend>
|
||||
<hr />
|
||||
<!--#for $msgid in $bookmarks_list#-->
|
||||
<a href="https://$newzbin_url/browse/post/$msgid/" target="_blank">$msgid</a>
|
||||
<!--#end for#-->
|
||||
<br class="clear" />
|
||||
</fieldset>
|
||||
<!--#end if#-->
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
<br/><hr/>
|
||||
<a href="${helpuri}Configure+Indexers-0-7" id="help" target="_blank">$T('menu-help')</a>
|
||||
<h3>NzbMatrix</h3><br/>
|
||||
|
||||
$T('explain-nzbmatrix')<br/>
|
||||
|
||||
@@ -79,6 +79,7 @@ MochiKit.DOM.addLoadEvent(location = "../../#config-rss");
|
||||
<thead>
|
||||
<tr>
|
||||
<th> </th>
|
||||
<th> </th>
|
||||
<th>$T('rss-order')</th>
|
||||
<th>$T('rss-type')</th>
|
||||
<th>$T('rss-filter')</th>
|
||||
@@ -92,6 +93,7 @@ MochiKit.DOM.addLoadEvent(location = "../../#config-rss");
|
||||
<tbody>
|
||||
<tr id="$feed+new_filter">
|
||||
<td></td>
|
||||
<td><input type="checkbox" name="enabled" value="1" checked="checked" /></td>
|
||||
<td></td>
|
||||
<td>
|
||||
<select name="filter_type">
|
||||
@@ -157,7 +159,9 @@ MochiKit.DOM.addLoadEvent(location = "../../#config-rss");
|
||||
<td>
|
||||
<input type="submit" value="$T('rss-delFilter')" onclick="javascript:lr('config/rss/del_rss_filter','index=$fnum&feed=$feed')" />
|
||||
</td>
|
||||
|
||||
<td>
|
||||
<input type="checkbox" name="enabled" value="1" <!--#if $filter[6] == '1' then 'checked="checked"' else ""#--> />
|
||||
</td>
|
||||
<td>
|
||||
<input type="text" size="3" name="new_index" value=$fnum>
|
||||
</td>
|
||||
@@ -213,6 +217,7 @@ MochiKit.DOM.addLoadEvent(location = "../../#config-rss");
|
||||
<input type="hidden" name="index" value="$fnum"/>
|
||||
<input type="hidden" name="feed" value="$feed"/>
|
||||
<input type="submit" value="$T('button-save')" onclick="javascript:submitconfig('config/rss/upd_rss_filter', this,'$feed+$fnum','1' )"/>
|
||||
<!--#if not $rss[$feed].filter_states[$fnum]#--> $T('Incorrect filter')<!--#end if#-->
|
||||
</td>
|
||||
|
||||
</tr>
|
||||
|
||||
@@ -26,17 +26,14 @@ else:
|
||||
<!--#end for#-->
|
||||
</select>
|
||||
<br class="clear" />
|
||||
<label class="label">$T('sch-frequency'):</label>
|
||||
<select name="dayofweek">
|
||||
<option value="*" selected>$T('daily')
|
||||
<option value="1">$T('monday')
|
||||
<option value="2">$T('tuesday')
|
||||
<option value="3">$T('wednesday')
|
||||
<option value="4">$T('thursday')
|
||||
<option value="5">$T('friday')
|
||||
<option value="6">$T('saturday')
|
||||
<option value="7">$T('sunday')
|
||||
</select>
|
||||
<label class="label" for="daysofweek">$T('sch-frequency'):</label>
|
||||
<input type="checkbox" name="daysofweek" value="1">$T('monday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="2">$T('tuesday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="3">$T('wednesday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="4">$T('thursday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="5">$T('friday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="6">$T('saturday')<br/>
|
||||
<input type="checkbox" name="daysofweek" value="7">$T('sunday')<br/>
|
||||
<br class="clear" />
|
||||
<label class="label">$T('sch-action'):</label>
|
||||
<select name="action">
|
||||
|
||||
@@ -808,7 +808,7 @@ function lrb(url, extra, refresh)
|
||||
{
|
||||
method:'POST',
|
||||
sendContent:values,
|
||||
headers: {"Content-Type":"application/x-www-form-urlencoded"}
|
||||
headers: {"Content-Type":"application/x-www-form-urlencoded", "Cache-Control": "no-cache"}
|
||||
|
||||
});
|
||||
d.addCallback(function(d)
|
||||
@@ -840,7 +840,7 @@ function lrb(url, extra, refresh)
|
||||
{
|
||||
method:'POST',
|
||||
sendContent:values,
|
||||
headers: {"Content-Type":"application/x-www-form-urlencoded"}
|
||||
headers: {"Content-Type":"application/x-www-form-urlencoded", "Cache-Control": "no-cache"}
|
||||
|
||||
});
|
||||
if (saveelement) {
|
||||
@@ -1133,7 +1133,9 @@ function loadingJSON(){
|
||||
<li><a class="config" href="$prefix/config/scheduling/" onclick="lr('config/scheduling/','', 0, 0);">$T('cmenu-scheduling')</a> </li>
|
||||
<li><a class="config" href="$prefix/config/rss/" onclick="lr('config/rss/','', 0, 0);">$T('cmenu-rss')</a> </li>
|
||||
<li><a class="config" href="$prefix/config/notify/" onclick="lr('config/notify/','', 0, 0);">$T('cmenu-notif')</a></li>
|
||||
<!--#if 0#-->
|
||||
<li><a class="config" href="$prefix/config/indexers/" onclick="lr('config/indexers/', '', 0, 0);">$T('cmenu-newzbin')</a></li>
|
||||
<!--#end if#-->
|
||||
<li><a class="config" href="$prefix/config/categories/" onclick="lr('config/categories/', '', 0, 0);">$T('cmenu-cat')</a></li>
|
||||
<li><a class="config" href="$prefix/config/sorting/" onclick="lr('config/sorting/', '', 0, 0);">$T('cmenu-sorting')</a></li>
|
||||
</ul>
|
||||
@@ -1152,9 +1154,6 @@ function loadingJSON(){
|
||||
<li><a class="config" onclick="javascript:timedPause()">$T("smpl-custom")</a></li>
|
||||
|
||||
</ul>
|
||||
<!--#if $varExists('newzbinDetails')#-->
|
||||
<li><a onclick="getBookmarks()">$T('smpl-getbookmarks')</a></li>
|
||||
<!--#end if#-->
|
||||
<!--#if $have_quota#-->
|
||||
<li><a onclick="resetQuota()">$T('link-resetQuota')</a></li>
|
||||
<!--#end if#-->
|
||||
@@ -1183,7 +1182,7 @@ function loadingJSON(){
|
||||
<div id="RightContainer" class="left-border">
|
||||
<div id="addNew" class="centerLinks" style="overflow: hidden; display: none;">
|
||||
<form action="addID" method="get">
|
||||
<input type="text" style="width:218px;" name="id" value="$T('enterURL')<!--#if $varExists('newzbinDetails') then $T('enterID') else '' #-->" onfocus="clearForm(this, 'Enter URL<!--#if $varExists('newzbinDetails') then " or Report ID" else "" #-->')" onblur="setForm(this, 'Enter URL<!--#if $varExists('newzbinDetails') then " or Report ID" else "" #-->')">
|
||||
<input type="text" style="width:218px;" name="id" value="$T('enterURL')" onfocus="clearForm(this, 'Enter URL<!--#if $varExists('newzbinDetails') then " or Report ID" else "" #-->')" onblur="setForm(this, 'Enter URL<!--#if $varExists('newzbinDetails') then " or Report ID" else "" #-->')">
|
||||
<!--#if $cat_list#-->
|
||||
<select name="cat" >
|
||||
<optgroup label="$T('category')">
|
||||
|
||||
@@ -24,15 +24,15 @@ border-top: 1px dotted #222;
|
||||
}
|
||||
|
||||
#progressBar {
|
||||
background-color: #fff;
|
||||
border: 1px solid #000;
|
||||
background-color: #fff;
|
||||
border: 1px solid #000;
|
||||
}
|
||||
#progressBartop {
|
||||
background-color: #fff;
|
||||
border: 1px solid #ccc;
|
||||
background-color: #fff;
|
||||
border: 1px solid #ccc;
|
||||
}
|
||||
#percentageBar {
|
||||
background-color: #4B4545;
|
||||
background-color: #4B4545;
|
||||
}
|
||||
|
||||
|
||||
@@ -83,7 +83,7 @@ table{border-spacing:0;}
|
||||
|
||||
|
||||
|
||||
input, select {
|
||||
input, select, option {
|
||||
background-color:#232323;
|
||||
border-color:#3a3a3a;
|
||||
color:white;
|
||||
@@ -110,4 +110,4 @@ span.unselected {
|
||||
color: white;
|
||||
background-color:#333;
|
||||
border: 1px solid #555;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,35 +0,0 @@
|
||||
<!--#include $webdir + "/inc_top.tmpl"#-->
|
||||
<script type="text/javascript" src="static/javascript/jquery.js"></script>
|
||||
<script type="text/javascript" src="static/javascript/restart.js"></script>
|
||||
<br/><br/>
|
||||
<h4 id="restarting" class="align-center">$T('wizard-restarting')</h4>
|
||||
<h4 id="complete" class="align-center success hidden">$T('wizard-complete')</h4>
|
||||
<br />
|
||||
<br/>
|
||||
<div id="tips" class="hidden">
|
||||
$T('wizard-tip1') <span class="bold">$T('wizard-tip2')</span><br/>
|
||||
<!--#if len($urls) > 1#--><!--#set $s = 's'#--><!--#else#--><!--#set $s = ''#--><!--#end if#-->
|
||||
<!--#set $tip3 = $T('wizard-tip3') % $s#-->
|
||||
$tip3:<br/><br/>
|
||||
<div class="quoteBlock">
|
||||
<!--#set $i = 0#-->
|
||||
<!--#for $url in $urls#-->
|
||||
<!--#set $i = $i+1#-->
|
||||
<a href="$url">$url</a><!--#if $i != len($urls)#--><br /><!--#end if#-->
|
||||
<!--#end for#-->
|
||||
</div><br/>
|
||||
$T('wizard-tip4')
|
||||
<br/><br/>
|
||||
$T('wizard-tip-wiki') <a href="$helpuri">wiki</a>
|
||||
</div>
|
||||
</div>
|
||||
<hr /><br/>
|
||||
<div class="full-width">
|
||||
<table class="full-width">
|
||||
<tr class="align-center">
|
||||
<td><input type="hidden" name="session" id="apikey" value="$session"><input class="bigbutton disabled" type="button" onclick="document.location ='$access_url'" value="$T('wizard-goto')" disabled="disabled"/></td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
|
||||
<!--#include $webdir + "/inc_bottom.tmpl"#-->
|
||||
@@ -31,7 +31,7 @@ $T('wizard-explain-server')
|
||||
<div id="connections-tip" class="tips">$T('wizard-server-con-explain') $T('wizard-server-con-eg')</div>
|
||||
<div id="connections-error" class="error-text hidden">$T('wizard-server-number')</div>
|
||||
<br class="clear" />
|
||||
<label><span class="label">$T('srv-ssl')</span>
|
||||
<label for="srv-ssl"><!--#if $have_ssl then $T('srv-ssl') else '<span class="disabled-text">'+$T('srv-ssl')+'</span> (pyopenssl (python-ssl) '+$T('opt-notInstalled')+')'#-->
|
||||
<input class="validate-text" class="radio" type="checkbox" name="ssl" value="1" <!--#if $have_ssl then '' else 'disabled'#--><!--#if $ssl == 1 then 'checked' else ''#-->></label>
|
||||
<div class="tips">$T('wizard-server-ssl-explain')</div>
|
||||
<br class="clear" />
|
||||
|
||||
@@ -1,39 +1,34 @@
|
||||
<!--#include $webdir + "/inc_top.tmpl"#-->
|
||||
|
||||
<form action="./four" method="post" autocomplete="off">
|
||||
<p>$T('wizard-index-explain')</p>
|
||||
<div id="serverDetails">
|
||||
<h3><a href="http://$newzbin_url" target="_blank">Newzbin2.es</a> ($T('wizard-optional'))</h3>
|
||||
<label class="label">$T('srv-username'):</label><input type="text" size="20" value="$newzbin_user" name="newzbin_user">
|
||||
<br class="clear" />
|
||||
<label class="label">$T('srv-password'):</label><input type="password" size="20" value="$newzbin_pass" name="newzbin_pass">
|
||||
<br class="clear" />
|
||||
<input type="checkbox" name="newzbin_bookmarks" id="newzbin_bookmarks" value="1" <!--#if $newzbin_bookmarks == 1 then 'checked="checked"' else ''#-->> <label for="newzbin_bookmarks">$T('wizard-index-bookmark')</label><br />
|
||||
|
||||
|
||||
<h3><a href="http://nzbmatrix.com" target="_blank">NZBMatrix.com</a> ($T('wizard-optional'))</h3>
|
||||
<label class="label">$T('srv-username'):</label><input type="text" size="20" value="$matrix_user" name="matrix_user">
|
||||
<br class="clear" />
|
||||
<label class="label">$T('opt-apikey'):</label><input type="text" size="20" value="$matrix_apikey" name="matrix_apikey">
|
||||
</div></div>
|
||||
|
||||
<script type="text/javascript" src="static/javascript/jquery.js"></script>
|
||||
<script type="text/javascript" src="static/javascript/restart.js"></script>
|
||||
<br/><br/>
|
||||
<h4 id="restarting" class="align-center">$T('wizard-restarting')</h4>
|
||||
<h4 id="complete" class="align-center success hidden">$T('wizard-complete')</h4>
|
||||
<br />
|
||||
<br/>
|
||||
<div id="tips" class="hidden">
|
||||
$T('wizard-tip1') <span class="bold">$T('wizard-tip2')</span><br/>
|
||||
<!--#set $tip3 = $T('wizard-tip3') % ''#-->
|
||||
$tip3<br/><br/>
|
||||
<div class="quoteBlock">
|
||||
<!--#set $i = 0#-->
|
||||
<!--#for $url in $urls#-->
|
||||
<!--#set $i = $i+1#-->
|
||||
<a href="$url">$url</a><!--#if $i != len($urls)#--><br /><!--#end if#-->
|
||||
<!--#end for#-->
|
||||
</div><br/>
|
||||
$T('wizard-tip4')
|
||||
<br/><br/>
|
||||
$T('wizard-tip-wiki') <a href="$helpuri">wiki</a>
|
||||
</div>
|
||||
</div>
|
||||
<hr /><br/>
|
||||
<div class="full-width">
|
||||
<table class="full-width">
|
||||
<tr>
|
||||
<td><input class="bigbutton" type="button" onclick="document.location ='./two'" value="‹ $T('wizard-previous')" /></td>
|
||||
<td>
|
||||
<div class="align-center">
|
||||
<!--#for $step in xrange($steps)#-->
|
||||
<!--#set $step = $step + 1#-->
|
||||
<span class="<!--#if $step == $number then 'selected' else 'unselected'#-->">$step</span>
|
||||
<!--#end for#-->
|
||||
</div>
|
||||
</td>
|
||||
<td class="align-right"><input class="bigbutton" type="submit" value="$T('wizard-next') »" /></td>
|
||||
<tr class="align-center">
|
||||
<td><input type="hidden" name="session" id="apikey" value="$session"><input class="bigbutton disabled" type="button" onclick="document.location ='$access_url'" value="$T('wizard-goto')" disabled="disabled"/></td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<!--#include $webdir + "/inc_bottom.tmpl"#-->
|
||||
<!--#include $webdir + "/inc_bottom.tmpl"#-->
|
||||
103
make_dmg.py
Normal file
@@ -0,0 +1,103 @@
|
||||
#!/usr/bin/env python -OO
|
||||
#
|
||||
# Copyright 2008-2012 The SABnzbd-Team <team@sabnzbd.org>
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU General Public License
|
||||
# as published by the Free Software Foundation; either version 2
|
||||
# of the License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
#
|
||||
|
||||
import os
|
||||
import sys
|
||||
import re
|
||||
|
||||
if len(sys.argv) < 2:
|
||||
print 'Usage: %s <release>' % os.path.split(sys.argv[0])[1]
|
||||
exit(1)
|
||||
|
||||
# Setup file names
|
||||
release = sys.argv[1]
|
||||
prod = 'SABnzbd-' + release
|
||||
fileDmg = prod + '-osx.dmg'
|
||||
fileOSr = prod + '-osx-src.tar.gz'
|
||||
fileImg = prod + '.sparseimage'
|
||||
builds = ('sl', 'lion', 'ml')
|
||||
build_folders = (
|
||||
'OS X 10.5 and 10.6 (Leopards)',
|
||||
'OS X 10.7 (Lion)',
|
||||
'OS X 10.8 (Mountain Lion)'
|
||||
)
|
||||
|
||||
# Check presense of all builds
|
||||
build_paths = []
|
||||
for build in builds:
|
||||
path = os.path.join(os.environ['HOME'], 'project/osx/%s-%s.cpio' % (prod, build))
|
||||
if os.path.exists(path):
|
||||
build_paths.append(path)
|
||||
else:
|
||||
print 'Missing build %s' % path
|
||||
exit(1)
|
||||
|
||||
# Create sparseimage from template
|
||||
os.system("unzip -o osx/image/template.sparseimage.zip")
|
||||
os.rename('template.sparseimage', fileImg)
|
||||
|
||||
# mount sparseimage and modify volume label
|
||||
os.system("hdiutil mount %s | grep /Volumes/SABnzbd >mount.log" % fileImg)
|
||||
|
||||
# Rename the volume
|
||||
fp = open('mount.log', 'r')
|
||||
data = fp.read()
|
||||
fp.close()
|
||||
os.remove('mount.log')
|
||||
m = re.search(r'/dev/(\w+)\s+', data)
|
||||
volume = 'SABnzbd-' + str(release)
|
||||
os.system('diskutil rename %s %s' % (m.group(1), volume))
|
||||
|
||||
authority = os.environ.get('SIGNING_AUTH')
|
||||
|
||||
# Unpack build into image and sign if possible
|
||||
for build in xrange(len(builds)):
|
||||
vol_path = '/Volumes/%s/%s/' % (volume, build_folders[build])
|
||||
os.system('ditto -x -z "%s" "%s"' % (build_paths[build], vol_path))
|
||||
if authority:
|
||||
app_name = '%s-%s' % (volume, builds[build])
|
||||
os.system('codesign -f -i "%s" -s "%s" "%s/SABnzbd.app"' % (app_name, authority, vol_path))
|
||||
|
||||
|
||||
# Put README.rtf in root
|
||||
from_path = '/Volumes/%s/%s/SABnzbd.app/Contents/Resources/Credits.rtf' % (volume, build_folders[0])
|
||||
to_path = '/Volumes/%s/README.rtf' % volume
|
||||
os.system('cp "%s" "%s"' % (from_path, to_path))
|
||||
|
||||
# Unmount sparseimage
|
||||
print 'Eject volume'
|
||||
os.system("hdiutil eject /Volumes/%s/>/dev/null" % volume)
|
||||
|
||||
print 'Wait 1 second'
|
||||
os.system("sleep 1")
|
||||
|
||||
# Convert sparseimage to read-only compressed dmg
|
||||
print 'Create DMG file'
|
||||
if os.path.exists(fileDmg):
|
||||
os.remove(fileDmg)
|
||||
os.system("hdiutil convert %s -format UDBZ -o %s>/dev/null" % (fileImg, fileDmg))
|
||||
|
||||
# Remove sparseimage
|
||||
os.system("rm %s>/dev/null" % fileImg)
|
||||
|
||||
print 'Make image internet-enabled'
|
||||
os.system("hdiutil internet-enable %s" % fileDmg)
|
||||
|
||||
print 'Copy GZ file'
|
||||
os.system('cp ~/project/osx/%s .' % fileOSr)
|
||||
|
Before Width: | Height: | Size: 64 KiB |
|
Before Width: | Height: | Size: 388 B |
BIN
osx/resources/sab_clicked.tiff
Normal file
|
Before Width: | Height: | Size: 902 B |
BIN
osx/resources/sab_idle.tiff
Normal file
|
Before Width: | Height: | Size: 1.1 KiB |
BIN
osx/resources/sab_pause.tiff
Normal file
BIN
osx/unrar/unrar
241
package.py
@@ -34,12 +34,13 @@ except ImportError:
|
||||
try:
|
||||
import py2app
|
||||
from setuptools import setup
|
||||
OSX_LION = [int(n) for n in platform.mac_ver()[0].split('.')] >= [10, 7, 0]
|
||||
OSX_SL = not OSX_LION and [int(n) for n in platform.mac_ver()[0].split('.')] >= [10, 6, 0]
|
||||
OSX_LEOPARD = not (OSX_LION or OSX_SL)
|
||||
OSX_ML = [int(n) for n in platform.mac_ver()[0].split('.')] >= [10, 8, 0]
|
||||
OSX_LION = not OSX_ML and [int(n) for n in platform.mac_ver()[0].split('.')] >= [10, 7, 0]
|
||||
OSX_SL = not OSX_LION and not OSX_ML
|
||||
class WindowsError (): pass
|
||||
except ImportError:
|
||||
py2app = None
|
||||
|
||||
OSX_ML = OSX_LION = OSX_SL = False
|
||||
|
||||
VERSION_FILE = 'sabnzbd/version.py'
|
||||
VERSION_FILEAPP = 'osx/resources/InfoPlist.strings'
|
||||
@@ -47,8 +48,8 @@ VERSION_FILEAPP = 'osx/resources/InfoPlist.strings'
|
||||
my_version = 'unknown'
|
||||
my_baseline = 'unknown'
|
||||
|
||||
def DeleteFiles(name):
|
||||
''' Delete one file or set of files from wild-card spec '''
|
||||
def delete_files(name):
|
||||
""" Delete one file or set of files from wild-card spec """
|
||||
for f in glob.glob(name):
|
||||
try:
|
||||
if os.path.exists(f):
|
||||
@@ -95,7 +96,7 @@ def PatchVersion(name):
|
||||
try:
|
||||
pipe = subprocess.Popen(GitStatus, shell=True, stdout=subprocess.PIPE).stdout
|
||||
for line in pipe.read().split('\n'):
|
||||
if 'nothing to commit' in line:
|
||||
if 'nothing to commit' in line or 'nothing added to commit' in line:
|
||||
state = ''
|
||||
break
|
||||
pipe.close()
|
||||
@@ -151,8 +152,7 @@ def PairList(src):
|
||||
lst.append((path, flist))
|
||||
else:
|
||||
path, name = os.path.split(item)
|
||||
items = []
|
||||
items.append(name)
|
||||
items = [name]
|
||||
lst.append((path, items))
|
||||
return lst
|
||||
|
||||
@@ -207,7 +207,7 @@ def Dos2Unix(name):
|
||||
def Unix2Dos(name):
|
||||
""" Read file, remove \r, replace \n by \r\n and write back """
|
||||
base, ext = os.path.splitext(name)
|
||||
if ext.lower() not in ('.py', '.txt', '.css', '.js', '.tmpl', '.sh', '.cmd'):
|
||||
if ext.lower() not in ('.py', '.txt', '.css', '.js', '.tmpl', '.sh', '.cmd', '.mkd'):
|
||||
return
|
||||
|
||||
print name
|
||||
@@ -230,9 +230,9 @@ def Unix2Dos(name):
|
||||
|
||||
|
||||
def rename_file(folder, old, new):
|
||||
oldpath = "%s/%s" % (folder, old)
|
||||
newpath = "%s/%s" % (folder, new)
|
||||
try:
|
||||
oldpath = "%s/%s" % (folder, old)
|
||||
newpath = "%s/%s" % (folder, new)
|
||||
if os.path.exists(newpath):
|
||||
os.remove(newpath)
|
||||
os.rename(oldpath, newpath)
|
||||
@@ -246,6 +246,11 @@ print sys.argv[0]
|
||||
Git = CheckPath('git')
|
||||
ZipCmd = CheckPath('zip')
|
||||
UnZipCmd = CheckPath('unzip')
|
||||
if os.name != 'nt':
|
||||
PanDoc = CheckPath('pandoc')
|
||||
else:
|
||||
PanDoc = None
|
||||
|
||||
if os.name == 'nt':
|
||||
msg = 'Requires the standard version of NSIS'
|
||||
NSIS = CheckPath('makensis')
|
||||
@@ -254,7 +259,7 @@ if os.name == 'nt':
|
||||
os.system('%s >%s' % (NSIS, log))
|
||||
if 'Unicode' not in open(log).read():
|
||||
msg = ''
|
||||
DeleteFiles(log)
|
||||
delete_files(log)
|
||||
if msg:
|
||||
print msg
|
||||
exit(1)
|
||||
@@ -293,11 +298,14 @@ Win32TempName = 'SABnzbd-windows.exe'
|
||||
fileIns = prod + '-win32-setup.exe'
|
||||
fileBin = prod + '-win32-bin.zip'
|
||||
fileSrc = prod + '-src.tar.gz'
|
||||
fileDmg = prod + '-osx.dmg'
|
||||
fileDmgLp = prod + '-osx-leopard.dmg'
|
||||
fileDmg_ml = prod + '-osx-mountainlion.dmg'
|
||||
fileDmg_lion = prod + '-osx-lion.dmg'
|
||||
fileDmg_sl = prod + '-osx-snowleopard.dmg'
|
||||
fileOSr = prod + '-osx-src.tar.gz'
|
||||
fileImg = prod + '.sparseimage'
|
||||
|
||||
if OSX_SL: postfix = 'sl'
|
||||
if OSX_LION: postfix = 'lion'
|
||||
if OSX_ML: postfix = 'ml'
|
||||
|
||||
PatchVersion(release)
|
||||
|
||||
@@ -305,7 +313,7 @@ PatchVersion(release)
|
||||
# List of data elements, directories end with a '/'
|
||||
data_files = [
|
||||
'ABOUT.txt',
|
||||
'README.txt',
|
||||
'README.mkd',
|
||||
'INSTALL.txt',
|
||||
'GPL2.txt',
|
||||
'GPL3.txt',
|
||||
@@ -351,60 +359,30 @@ if target == 'app':
|
||||
os.system(GitRevertVersion)
|
||||
exit(1)
|
||||
|
||||
if not PanDoc:
|
||||
print "Sorry, requires pandoc in the $PATH"
|
||||
os.system(GitRevertVersion)
|
||||
exit(1)
|
||||
|
||||
# Check which Python flavour
|
||||
apple_py = 'ActiveState' not in sys.copyright
|
||||
|
||||
#Create sparseimage from template
|
||||
os.system("unzip osx/image/template.sparseimage.zip")
|
||||
os.rename('sabnzbd-template.sparseimage', fileImg)
|
||||
|
||||
#mount sparseimage and modify volume label
|
||||
os.system("hdiutil mount %s | grep /Volumes/SABnzbd >mount.log" % (fileImg))
|
||||
|
||||
# Select OSX version specific background image
|
||||
# Take care to preserve the special attributes of the background image file
|
||||
if OSX_LION:
|
||||
# Lion and higher: generates SnowLeopard/Lion DMG
|
||||
f = open('osx/image/sabnzbd.png', 'rb')
|
||||
png = f.read()
|
||||
f.close()
|
||||
else:
|
||||
# Snow Leopard and lower: generates Leopard DMG
|
||||
fileDmg = fileDmgLp
|
||||
f = open('osx/image/sabnzbd_leopard.png', 'rb')
|
||||
png = f.read()
|
||||
f.close()
|
||||
f = open('/Volumes/SABnzbd/sabnzbd.png', 'wb')
|
||||
f.write(png)
|
||||
f.close()
|
||||
|
||||
# Rename the volume
|
||||
fp = open('mount.log', 'r')
|
||||
data = fp.read()
|
||||
fp.close()
|
||||
os.remove('mount.log')
|
||||
m = re.search(r'/dev/(\w+)\s+', data)
|
||||
volume = 'SABnzbd-' + str(my_version)
|
||||
os.system('disktool -n %s %s' % (m.group(1), volume))
|
||||
|
||||
options['description'] = 'SABnzbd ' + str(my_version)
|
||||
|
||||
#Create MO files
|
||||
os.system('python ./tools/make_mo.py all')
|
||||
# Remove previous build result
|
||||
os.system('rm -rf dist/ build/')
|
||||
|
||||
#build SABnzbd.py
|
||||
# Create MO files
|
||||
os.system('python ./tools/make_mo.py')
|
||||
|
||||
# build SABnzbd.py
|
||||
sys.argv[1] = 'py2app'
|
||||
|
||||
# Due to ApplePython bug
|
||||
if apple_py:
|
||||
sys.argv.append('-p')
|
||||
sys.argv.append('email')
|
||||
|
||||
APP = ['SABnzbd.py']
|
||||
DATA_FILES = ['interfaces', 'locale', 'email', ('', glob.glob("osx/resources/*"))]
|
||||
|
||||
NZBFILE = dict(
|
||||
CFBundleTypeExtensions = [ "nzb","zip","rar" ],
|
||||
CFBundleTypeExtensions = [ "nzb" ],
|
||||
CFBundleTypeIconFile = 'nzbfile.icns',
|
||||
CFBundleTypeMIMETypes = [ "text/nzb" ],
|
||||
CFBundleTypeName = 'NZB File',
|
||||
@@ -412,13 +390,19 @@ if target == 'app':
|
||||
LSTypeIsPackage = 0,
|
||||
NSPersistentStoreTypeKey = 'Binary',
|
||||
)
|
||||
OPTIONS = {'argv_emulation': not apple_py, 'iconfile': 'osx/resources/sabnzbdplus.icns', 'plist': {
|
||||
'NSUIElement':1,
|
||||
'CFBundleShortVersionString':release,
|
||||
'NSHumanReadableCopyright':'The SABnzbd-Team',
|
||||
'CFBundleIdentifier':'org.sabnzbd.team',
|
||||
'CFBundleDocumentTypes':[NZBFILE]
|
||||
}}
|
||||
OPTIONS = {'argv_emulation': not apple_py,
|
||||
'iconfile': 'osx/resources/sabnzbdplus.icns',
|
||||
'plist': {
|
||||
'NSUIElement':1,
|
||||
'CFBundleShortVersionString':release,
|
||||
'NSHumanReadableCopyright':'The SABnzbd-Team',
|
||||
'CFBundleIdentifier':'org.sabnzbd.team',
|
||||
'CFBundleDocumentTypes':[NZBFILE],
|
||||
},
|
||||
'packages': "email,xml,Cheetah",
|
||||
'excludes': ["pywin", "pywin.debugger", "pywin.debugger.dbgcon", "pywin.dialogs",
|
||||
"pywin.dialogs.list", "Tkconstants", "Tkinter", "tcl"]
|
||||
}
|
||||
|
||||
setup(
|
||||
app=APP,
|
||||
@@ -427,64 +411,69 @@ if target == 'app':
|
||||
setup_requires=['py2app'],
|
||||
)
|
||||
|
||||
#copy unrar & par2 binary to avoid striping
|
||||
# Remove 64bit code
|
||||
if not OSX_SL:
|
||||
os.system("mv dist/SABnzbd.app dist/SABnzbd.app.temp")
|
||||
os.system("ditto --arch i386 --arch ppc dist/SABnzbd.app.temp dist/SABnzbd.app/")
|
||||
os.system("rm -rf dist/SABnzbd.app.temp")
|
||||
|
||||
# copy unrar & par2 binary
|
||||
os.system("mkdir dist/SABnzbd.app/Contents/Resources/osx>/dev/null")
|
||||
os.system("mkdir dist/SABnzbd.app/Contents/Resources/osx/par2>/dev/null")
|
||||
os.system("cp -pR osx/par2/ dist/SABnzbd.app/Contents/Resources/osx/par2>/dev/null")
|
||||
os.system("mkdir dist/SABnzbd.app/Contents/Resources/osx/unrar>/dev/null")
|
||||
os.system("cp -pR osx/unrar/license.txt dist/SABnzbd.app/Contents/Resources/osx/unrar/ >/dev/null")
|
||||
if OSX_LION:
|
||||
os.system("cp -pR osx/unrar/unrar dist/SABnzbd.app/Contents/Resources/osx/unrar/ >/dev/null")
|
||||
else:
|
||||
if OSX_SL:
|
||||
os.system("cp -pR osx/unrar/unrar-leopard dist/SABnzbd.app/Contents/Resources/osx/unrar/unrar >/dev/null")
|
||||
else:
|
||||
os.system("cp -pR osx/unrar/unrar dist/SABnzbd.app/Contents/Resources/osx/unrar/ >/dev/null")
|
||||
os.system("cp icons/sabnzbd.ico dist/SABnzbd.app/Contents/Resources >/dev/null")
|
||||
os.system("cp README.rtf dist/SABnzbd.app/Contents/Resources/Credits.rtf >/dev/null")
|
||||
os.system("pandoc -f markdown -t rtf -s -o dist/SABnzbd.app/Contents/Resources/Credits.rtf README.mkd >/dev/null")
|
||||
os.system("find dist/SABnzbd.app -name .git | xargs rm -rf")
|
||||
|
||||
# Sign the App if possible
|
||||
authority = os.environ.get('SIGNING_AUTH')
|
||||
if authority:
|
||||
os.system('codesign -f -i "%s" -s "%s" dist/SABnzbd.app' % (volume, authority))
|
||||
# Remove source files to prevent re-compilation, which would invalidate signing
|
||||
py_ver = '%s.%s' % (sys.version_info[0], sys.version_info[1])
|
||||
os.system("find dist/SABnzbd.app/Contents/Resources/lib/python%s/Cheetah -name '*.py' | xargs rm" % py_ver)
|
||||
os.system("find dist/SABnzbd.app/Contents/Resources/lib/python%s/xml -name '*.py' | xargs rm" % py_ver)
|
||||
os.system('rm dist/SABnzbd.app/Contents/Resources/site.py')
|
||||
|
||||
# Add the SabNotifier app
|
||||
if OSX_ML and os.path.exists('/project/sabnotifier/SABnzbd.app'):
|
||||
os.system("cp -pR /project/sabnotifier/SABnzbd.app dist/SABnzbd.app/Contents/Resources/")
|
||||
|
||||
#copy app to mounted sparseimage
|
||||
os.system("cp -r dist/SABnzbd.app /Volumes/%s/>/dev/null" % volume)
|
||||
|
||||
print 'Create src %s' % fileOSr
|
||||
os.system('tar -czf %s --exclude ".git*" --exclude "sab*.zip" --exclude "SAB*.tar.gz" --exclude "*.cmd" --exclude "*.pyc" '
|
||||
'--exclude "*.sparseimage" --exclude "dist" --exclude "build" --exclude "*.nsi" --exclude "win" --exclude "*.dmg" '
|
||||
'./ >/dev/null' % (fileOSr) )
|
||||
|
||||
# Copy README.txt
|
||||
os.system("cp README.rtf /Volumes/%s/" % volume)
|
||||
|
||||
# Remove site.py to prevent re-compilation (otherwise the OSX Firewall may complain)
|
||||
os.remove('/Volumes/%s/SABnzbd.app/Contents/Resources/site.py' % volume)
|
||||
|
||||
#Unmount sparseimage
|
||||
os.system("hdiutil eject /Volumes/%s/>/dev/null" % volume)
|
||||
# Add License files
|
||||
os.mkdir("dist/SABnzbd.app/Contents/Resources/licenses/")
|
||||
os.system("cp -p licenses/*.txt dist/SABnzbd.app/Contents/Resources/licenses/")
|
||||
os.system("cp -p *.txt dist/SABnzbd.app/Contents/Resources/licenses/")
|
||||
|
||||
os.system("sleep 5")
|
||||
#Convert sparseimage to read only compressed dmg
|
||||
if os.path.exists(fileDmg):
|
||||
os.remove(fileDmg)
|
||||
os.system("hdiutil convert %s -format UDBZ -o %s>/dev/null" % (fileImg, fileDmg))
|
||||
#Remove sparseimage
|
||||
os.system("rm %s>/dev/null" % (fileImg))
|
||||
|
||||
#Make image internet-enabled
|
||||
os.system("hdiutil internet-enable %s" % fileDmg)
|
||||
# Archive result to share
|
||||
dest_path = '/Volumes/VMware Shared Folders/osx'
|
||||
if not os.path.exists(dest_path):
|
||||
dest_path = '$HOME/project/osx'
|
||||
cpio_path = os.path.join(dest_path, prod) + '-' + postfix + '.cpio'
|
||||
print 'Create CPIO file %s' % cpio_path
|
||||
delete_files(cpio_path)
|
||||
os.system('ditto -c -z dist/ "%s"' % cpio_path)
|
||||
|
||||
if OSX_ML:
|
||||
print 'Create src %s' % fileOSr
|
||||
delete_files(fileOSr)
|
||||
os.system('tar -czf %s --exclude ".git*" --exclude "sab*.zip" --exclude "SAB*.tar.gz" --exclude "*.cmd" --exclude "*.pyc" '
|
||||
'--exclude "*.sparseimage*" --exclude "dist" --exclude "build" --exclude "*.nsi" --exclude "win" --exclude "*.dmg" '
|
||||
'./ >/dev/null' % os.path.join(dest_path, fileOSr) )
|
||||
|
||||
os.system(GitRevertApp + VERSION_FILEAPP)
|
||||
os.system(GitRevertApp + VERSION_FILE)
|
||||
|
||||
|
||||
elif target in ('binary', 'installer'):
|
||||
if not py2exe:
|
||||
print "Sorry, only works on Windows!"
|
||||
os.system(GitRevertVersion)
|
||||
exit(1)
|
||||
|
||||
#run_times = check_runtimes()
|
||||
|
||||
# Create MO files
|
||||
os.system('tools\\make_mo.py all')
|
||||
|
||||
@@ -518,12 +507,12 @@ elif target in ('binary', 'installer'):
|
||||
for tup in options['data_files']:
|
||||
for file in tup[1]:
|
||||
name, ext = os.path.splitext(file)
|
||||
if ext.lower() in ('.txt', '.cmd'):
|
||||
if ext.lower() in ('.txt', '.cmd', '.mkd'):
|
||||
Unix2Dos("dist/%s" % file)
|
||||
DeleteFiles('dist/Sample-PostProc.sh')
|
||||
DeleteFiles('dist/PKG-INFO')
|
||||
delete_files('dist/Sample-PostProc.sh')
|
||||
delete_files('dist/PKG-INFO')
|
||||
|
||||
DeleteFiles('*.ini')
|
||||
delete_files('*.ini')
|
||||
|
||||
############################
|
||||
# Generate the windowed-app
|
||||
@@ -560,37 +549,40 @@ elif target in ('binary', 'installer'):
|
||||
|
||||
############################
|
||||
# Remove unwanted system DLL files that Py2Exe copies when running on Win7
|
||||
DeleteFiles(r'dist\lib\API-MS-Win-*.dll')
|
||||
DeleteFiles(r'dist\lib\MSWSOCK.DLL')
|
||||
DeleteFiles(r'dist\lib\POWRPROF.DLL')
|
||||
delete_files(r'dist\lib\API-MS-Win-*.dll')
|
||||
delete_files(r'dist\lib\MSWSOCK.DLL')
|
||||
delete_files(r'dist\lib\POWRPROF.DLL')
|
||||
delete_files(r'dist\lib\KERNELBASE.dll')
|
||||
|
||||
############################
|
||||
# Remove .git residue
|
||||
DeleteFiles(r'dist\interfaces\Config\.git')
|
||||
delete_files(r'dist\interfaces\Config\.git')
|
||||
|
||||
############################
|
||||
# Copy MS runtime files or Curl
|
||||
if sys.version_info > (2, 5):
|
||||
#Won't work with OpenSSL DLLs :(
|
||||
#shutil.copy2(os.path.join(run_times, r'Microsoft.VC90.CRT.manifest'), r'dist')
|
||||
#shutil.copy2(os.path.join(run_times, r'msvcp90.dll'), r'dist')
|
||||
#shutil.copy2(os.path.join(run_times, r'msvcr90.dll'), r'dist')
|
||||
#shutil.copy2(os.path.join(run_times, r'lib\Microsoft.VC90.CRT.manifest'), r'dist\lib')
|
||||
pass
|
||||
else:
|
||||
# Copy Curl if needed
|
||||
if sys.version_info < (2, 6):
|
||||
# Curl for Python 2.5
|
||||
os.system(r'unzip -o win\curl\curl.zip -d dist\lib')
|
||||
|
||||
############################
|
||||
# Fix icon issue with NZB association
|
||||
os.system(r'copy dist\icons\nzb.ico dist')
|
||||
|
||||
############################
|
||||
# Rename MKD file
|
||||
rename_file('dist', 'README.mkd', 'README.txt')
|
||||
|
||||
############################
|
||||
if target == 'installer':
|
||||
|
||||
delete_files(fileIns)
|
||||
os.system('makensis.exe /v3 /DSAB_PRODUCT=%s /DSAB_VERSION=%s /DSAB_FILE=%s NSIS_Installer.nsi.tmp' % \
|
||||
(prod, release, fileIns))
|
||||
DeleteFiles('NSIS_Installer.nsi.tmp')
|
||||
delete_files('NSIS_Installer.nsi.tmp')
|
||||
if not os.path.exists(fileIns):
|
||||
print 'Fatal error creating %s' % fileIns
|
||||
exit(1)
|
||||
|
||||
DeleteFiles(fileBin)
|
||||
#write_dll_message('dist/IMPORTANT_MESSAGE.txt')
|
||||
delete_files(fileBin)
|
||||
os.rename('dist', prod)
|
||||
os.system('zip -9 -r -X %s %s' % (fileBin, prod))
|
||||
time.sleep(1.0)
|
||||
@@ -657,6 +649,10 @@ else:
|
||||
shutil.copy2(file, dest)
|
||||
Dos2Unix(fullname)
|
||||
|
||||
############################
|
||||
# Rename MKD file
|
||||
rename_file(root, 'README.mkd', 'README.txt')
|
||||
|
||||
os.chdir(root)
|
||||
os.chdir('..')
|
||||
|
||||
@@ -664,4 +660,3 @@ else:
|
||||
CreateTar('srcdist', fileSrc, prod)
|
||||
|
||||
os.system(GitRevertVersion)
|
||||
|
||||
|
||||
@@ -7,15 +7,15 @@ msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: sabnzbd\n"
|
||||
"Report-Msgid-Bugs-To: FULL NAME <EMAIL@ADDRESS>\n"
|
||||
"POT-Creation-Date: 2012-03-09 19:01+0000\n"
|
||||
"PO-Revision-Date: 2012-03-14 04:51+0000\n"
|
||||
"Last-Translator: Rene <Unknown>\n"
|
||||
"POT-Creation-Date: 2012-04-28 12:01+0000\n"
|
||||
"PO-Revision-Date: 2012-08-03 17:24+0000\n"
|
||||
"Last-Translator: shypike <Unknown>\n"
|
||||
"Language-Team: Danish <da@li.org>\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
"X-Launchpad-Export-Date: 2012-03-15 05:11+0000\n"
|
||||
"X-Generator: Launchpad (build 14933)\n"
|
||||
"X-Launchpad-Export-Date: 2012-08-04 05:38+0000\n"
|
||||
"X-Generator: Launchpad (build 15742)\n"
|
||||
|
||||
#: email/email.tmpl:1
|
||||
msgid ""
|
||||
@@ -65,42 +65,42 @@ msgid ""
|
||||
"<!--#end if#-->\n"
|
||||
msgstr ""
|
||||
"##\n"
|
||||
"## Default Email template for SABnzbd\n"
|
||||
"## This a Cheetah template\n"
|
||||
"## Documentation: http://sabnzbd.wikidot.com/email-templates\n"
|
||||
"## Standard Email skabelon til SABnzbd\n"
|
||||
"## Dette er en Cheetah skabelon\n"
|
||||
"## Dokumentation: http://sabnzbd.wikidot.com/email-templates\n"
|
||||
"##\n"
|
||||
"## Newlines and whitespace are significant!\n"
|
||||
"## Linjeskift og blanktegn er betydelig!\n"
|
||||
"##\n"
|
||||
"## These are the email headers\n"
|
||||
"## Disse er e-mail-headerne \n"
|
||||
"To: $to\n"
|
||||
"From: $from\n"
|
||||
"Date: $date\n"
|
||||
"Subject: SABnzbd has <!--#if $status then \"completed\" else \"failed\" #--> "
|
||||
"Subject: SABnzbd har <!--#if $status then \"hentet\" else \"fejlet\" #--> "
|
||||
"job $name\n"
|
||||
"X-priority: 5\n"
|
||||
"X-MS-priority: 5\n"
|
||||
"## After this comes the body, the empty line is required!\n"
|
||||
"## Efter dette kommer body, den tomme linje kræves!\n"
|
||||
"\n"
|
||||
"Hej,\n"
|
||||
"<!--#if $status #-->\n"
|
||||
"SABnzbd har downloaded \"$name\" <!--#if $msgid==\"\" then \"\" else "
|
||||
"\"(newzbin #\" + $msgid + \")\"#-->\n"
|
||||
"SABnzbd har hentet \"$name\" <!--#if $msgid==\"\" then \"\" else \"(newzbin "
|
||||
"#\" + $msgid + \")\"#-->\n"
|
||||
"<!--#else#-->\n"
|
||||
"SABnzbd har ikke downloaded \"$name\" <!--#if $msgid==\"\" then \"\" else "
|
||||
"SABnzbd kunne ikke hente \"$name\" <!--#if $msgid==\"\" then \"\" else "
|
||||
"\"(newzbin #\" + $msgid + \")\"#-->\n"
|
||||
"<!--#end if#-->\n"
|
||||
"Færdig kl. $end_time\n"
|
||||
"Downloaded $size\n"
|
||||
"Hentet $size\n"
|
||||
"\n"
|
||||
"Resultat af job:\n"
|
||||
"<!--#for $stage in $stages #-->\n"
|
||||
"Stage $stage <!--#slurp#-->\n"
|
||||
"Etape $stage <!--#slurp#-->\n"
|
||||
"<!--#for $result in $stages[$stage]#-->\n"
|
||||
" $result <!--#slurp#-->\n"
|
||||
"<!--#end for#-->\n"
|
||||
"<!--#end for#-->\n"
|
||||
"<!--#if $script!=\"\" #-->\n"
|
||||
"Output from user script \"$script\" (Exit code = $script_ret):\n"
|
||||
"Output fra bruger script \"$script\" (Exit code = $script_ret):\n"
|
||||
"$script_output\n"
|
||||
"<!--#end if#-->\n"
|
||||
"<!--#if $status #-->\n"
|
||||
@@ -138,20 +138,20 @@ msgid ""
|
||||
"Bye\n"
|
||||
msgstr ""
|
||||
"##\n"
|
||||
"## RSS Email template for SABnzbd\n"
|
||||
"## This a Cheetah template\n"
|
||||
"## Documentation: http://sabnzbd.wikidot.com/email-templates\n"
|
||||
"## RSS Email skabelon til SABnzbd\n"
|
||||
"## Dette er Cheetah skabelon\n"
|
||||
"## Dokumentation: http://sabnzbd.wikidot.com/email-templates\n"
|
||||
"##\n"
|
||||
"## Newlines and whitespace are significant!\n"
|
||||
"## Linjeskift og blanktegn er betydelig!\n"
|
||||
"##\n"
|
||||
"## These are the email headers\n"
|
||||
"## Dette er email headers\n"
|
||||
"To: $to\n"
|
||||
"From: $from\n"
|
||||
"Date: $date\n"
|
||||
"Subject: SABnzbd har tilføjet $antal jobs til køen\n"
|
||||
"X-priority: 5\n"
|
||||
"X-MS-priority: 5\n"
|
||||
"## After this comes the body, the empty line is required!\n"
|
||||
"## Efter dette kommer body, den tomme linje kræves!\n"
|
||||
"\n"
|
||||
"Hej,\n"
|
||||
"\n"
|
||||
@@ -189,24 +189,24 @@ msgid ""
|
||||
"Bye\n"
|
||||
msgstr ""
|
||||
"##\n"
|
||||
"## Bad URL Fetch Email template for SABnzbd\n"
|
||||
"## This a Cheetah template\n"
|
||||
"## Documentation: http://sabnzbd.wikidot.com/email-templates\n"
|
||||
"## Dårlig URL Fetch E-mail skabelon for SABnzbd\n"
|
||||
"## Dette er en Cheetah skabelon\n"
|
||||
"## Dokumentation: http://sabnzbd.wikidot.com/email-templates\n"
|
||||
"##\n"
|
||||
"## Newlines and whitespace are significant!\n"
|
||||
"## Linjeskift og blanktegn er betydelig!\n"
|
||||
"##\n"
|
||||
"## These are the email headers\n"
|
||||
"## Dette er email headers\n"
|
||||
"To: $to\n"
|
||||
"From: $from\n"
|
||||
"Date: $date\n"
|
||||
"Subject: SABnzbd failed to fetch an NZB\n"
|
||||
"Subject: SABnzbd kunne ikke hente en NZB\n"
|
||||
"X-priority: 5\n"
|
||||
"X-MS-priority: 5\n"
|
||||
"## After this comes the body, the empty line is required!\n"
|
||||
"## Efter dette kommer body, den tomme linje kræves!\n"
|
||||
"\n"
|
||||
"Hi,\n"
|
||||
"Hej,\n"
|
||||
"\n"
|
||||
"SABnzbd has failed to retrieve the NZB from $url.\n"
|
||||
"The error message was: $msg\n"
|
||||
"SABnzbd kunne ikke hente NZB fra $url.\n"
|
||||
"Fejl meddelelsen er: $msg\n"
|
||||
"\n"
|
||||
"Bye\n"
|
||||
"Farvel\n"
|
||||
|
||||
@@ -7,15 +7,15 @@ msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: sabnzbd\n"
|
||||
"Report-Msgid-Bugs-To: FULL NAME <EMAIL@ADDRESS>\n"
|
||||
"POT-Creation-Date: 2012-03-09 19:01+0000\n"
|
||||
"PO-Revision-Date: 2011-06-26 10:50+0000\n"
|
||||
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
|
||||
"POT-Creation-Date: 2012-04-28 12:01+0000\n"
|
||||
"PO-Revision-Date: 2012-12-28 10:58+0000\n"
|
||||
"Last-Translator: Thomas Lucke (Lucky) <Unknown>\n"
|
||||
"Language-Team: German <de@li.org>\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
"X-Launchpad-Export-Date: 2012-03-11 05:02+0000\n"
|
||||
"X-Generator: Launchpad (build 14914)\n"
|
||||
"X-Launchpad-Export-Date: 2012-12-29 05:11+0000\n"
|
||||
"X-Generator: Launchpad (build 16378)\n"
|
||||
|
||||
#: email/email.tmpl:1
|
||||
msgid ""
|
||||
@@ -189,3 +189,24 @@ msgid ""
|
||||
"\n"
|
||||
"Bye\n"
|
||||
msgstr ""
|
||||
"## Translation by Thomas Lucke (Lucky)\n"
|
||||
"##\n"
|
||||
"## Bad URL Fetch Email template for SABnzbd\n"
|
||||
"## This a Cheetah template\n"
|
||||
"## Documentation: http://sabnzbd.wikidot.com/email-templates\n"
|
||||
"##\n"
|
||||
"## Newlines and whitespace are significant!\n"
|
||||
"##\n"
|
||||
"## These are the email headers\n"
|
||||
"To: $to\n"
|
||||
"From: $from\n"
|
||||
"Date: $date\n"
|
||||
"Subject: SABnzbd konnte eine NZB-Datei nicht herunterladen\n"
|
||||
"X-priority: 5\n"
|
||||
"X-MS-priority: 5\n"
|
||||
"## After this comes the body, the empty line is required!\n"
|
||||
"\n"
|
||||
"Hallo,\n"
|
||||
"\n"
|
||||
"SABnzbd konnte die NZB-Datei von $url nicht herrunterladen.\n"
|
||||
"Die Fehlermeldung war: $msg\n"
|
||||
|
||||