2017-06-17 02:11:46 -07:00
package main
import (
2017-07-16 23:48:06 -07:00
"bufio"
2017-06-17 02:11:46 -07:00
"fmt"
2018-01-11 15:54:03 -08:00
"net"
2018-01-06 17:31:50 -08:00
"net/http"
2017-06-20 12:25:19 -07:00
"os"
2017-07-16 23:48:06 -07:00
"os/exec"
2017-08-08 11:07:36 -07:00
"path/filepath"
2018-01-06 17:31:50 -08:00
"sort"
"strconv"
2017-08-08 11:07:36 -07:00
"strings"
2018-01-06 17:31:50 -08:00
"time"
"timmy.narnian.us/git/timmy/scene"
2017-06-20 12:25:19 -07:00
"github.com/alexflint/go-arg"
2018-01-06 17:31:50 -08:00
"github.com/lordwelch/transmission"
2017-06-20 12:25:19 -07:00
)
var (
2018-01-06 17:31:50 -08:00
CurrentTorrents map [ string ] SeriesTorrent
unselectedDir string
Transmission * transmission . Client
2018-01-09 22:52:45 -08:00
CurrentHashes [ ] string
2018-01-06 17:31:50 -08:00
args struct {
RES string ` arg:"help:Resolution preference [480/720/1080]" `
RELEASE [ ] string ` arg:"-r,help:Release group preference order." `
NRELEASE [ ] string ` arg:"-R,help:Release groups to use only as a lost resort." `
TAGS [ ] string ` arg:"-t,help:Tags to prefer -t internal would choose an internal over another. Whichever file with the most tags is chosen. Release Group takes priority" `
Series [ ] string ` arg:"required,positional,help:TV series to download torrent file for" `
NEW bool ` arg:"-n,help:Only modify new torrents" `
PATH string ` arg:"-P,required,help:Path to torrent files" `
2018-01-09 22:52:45 -08:00
HOST string ` arg:"-H,help:Host for transmission" `
2018-01-06 17:31:50 -08:00
}
2017-06-17 02:11:46 -07:00
)
func main ( ) {
2017-07-23 23:21:25 -07:00
var (
2018-01-06 17:31:50 -08:00
stdC = make ( chan * SceneVideoTorrent )
2017-07-23 23:21:25 -07:00
)
2018-01-06 17:31:50 -08:00
initialize ( )
go stdinLoop ( stdC )
2017-09-22 17:47:50 -07:00
2018-01-09 22:52:45 -08:00
for i := 0 ; true ; {
i ++
fmt . Println ( i )
2018-01-06 17:31:50 -08:00
select {
case <- time . After ( time . Minute * 15 ) :
download ( )
case current := <- stdC :
addtorrent ( CurrentTorrents [ current . Title ] , current )
}
2017-09-22 17:47:50 -07:00
}
2018-01-06 17:31:50 -08:00
}
2017-09-22 17:47:50 -07:00
2018-01-06 17:31:50 -08:00
func stdinLoop ( C chan * SceneVideoTorrent ) {
2017-07-22 22:53:12 -07:00
scanner := bufio . NewScanner ( os . Stdin )
2017-08-08 11:07:36 -07:00
for scanner . Scan ( ) {
url := strings . TrimSpace ( scanner . Text ( ) )
2018-01-09 22:52:45 -08:00
fmt . Println ( "url:" , url )
2018-01-06 17:31:50 -08:00
torrentName := filepath . Base ( url )
torrentPath := filepath . Join ( unselectedDir , torrentName )
_ , err := os . Stat ( torrentPath )
if ! os . IsNotExist ( err ) {
2018-01-11 15:54:03 -08:00
fmt . Println ( err )
2018-01-06 17:31:50 -08:00
continue
}
2017-11-30 19:41:28 -08:00
cmd := exec . Command ( "wget" , url , "-q" , "-O" , torrentPath )
2017-11-30 18:38:02 -08:00
cmd . Stdout = os . Stdout
cmd . Stderr = os . Stderr
2018-01-06 17:31:50 -08:00
err = cmd . Run ( )
2017-11-30 18:29:28 -08:00
if err != nil {
2017-08-08 11:07:36 -07:00
fmt . Println ( "url failed: " , url )
2017-11-30 18:29:28 -08:00
fmt . Println ( err )
2017-08-08 11:07:36 -07:00
continue
2017-07-16 23:48:06 -07:00
}
2018-01-09 22:52:45 -08:00
if filepath . Ext ( torrentPath ) == ".torrent" {
current := process ( torrentPath )
for _ , title := range args . Series {
if current . Title == title {
C <- current
break
}
}
}
2018-01-11 15:54:03 -08:00
fmt . Println ( "Torrent:" , torrentName )
2018-01-09 22:52:45 -08:00
}
}
// Get hashes of torrents that were previously selected then remove the link to them
2018-01-11 15:54:03 -08:00
func getLinks ( ) ( hash [ ] string ) {
// get files in selected dir
2018-01-09 22:52:45 -08:00
selectedDir := filepath . Join ( unselectedDir , "../" )
selectedFolder , _ := os . Open ( selectedDir )
defer selectedFolder . Close ( )
selectedNames , _ := selectedFolder . Readdirnames ( 0 )
2018-01-11 15:54:03 -08:00
// Add hashes of currently selected torrents
2018-01-09 22:52:45 -08:00
for _ , lnk := range selectedNames {
target , err := os . Readlink ( filepath . Join ( selectedDir , lnk ) )
if err == nil {
if filepath . Base ( filepath . Dir ( target ) ) == "unselected" {
hash = append ( hash , process ( target ) . Meta . Hash )
2018-01-06 17:31:50 -08:00
}
}
}
2018-01-09 22:52:45 -08:00
selectedNames , _ = selectedFolder . Readdirnames ( 0 )
fmt . Println ( selectedNames )
return
2018-01-06 17:31:50 -08:00
}
func download ( ) {
2018-01-11 15:54:03 -08:00
var (
run bool = true
err error
)
hash := getLinks ( )
2018-01-09 22:52:45 -08:00
if Transmission != nil {
stopDownloads ( hash )
}
2018-01-06 17:31:50 -08:00
for _ , s := range CurrentTorrents {
for _ , se := range s {
for _ , ep := range se {
2018-01-11 15:54:03 -08:00
var CurrentHash bool
for _ , HASH := range hash {
2018-01-13 14:03:46 -08:00
if HASH == ep . Ep [ 0 ] . Meta . Hash {
CurrentHash = HASH == ep . Ep [ 0 ] . Meta . Hash
break
}
2018-01-11 15:54:03 -08:00
}
if ! CurrentHash {
fmt . Printf ( "Better file found for: %s S%sE%s\n" , ep . Ep [ 0 ] . Title , ep . Ep [ 0 ] . Season , ep . Ep [ 0 ] . Episode )
os . Remove ( filepath . Join ( filepath . Join ( unselectedDir , "../" ) , filepath . Base ( ep . Ep [ 0 ] . Meta . FilePath ) ) )
os . Symlink ( ep . Ep [ 0 ] . Meta . FilePath , filepath . Join ( filepath . Join ( unselectedDir , "../" ) , filepath . Base ( ep . Ep [ 0 ] . Meta . FilePath ) ) )
}
2018-01-06 17:31:50 -08:00
}
}
}
2018-01-09 22:52:45 -08:00
if Transmission != nil {
time . Sleep ( time . Second * 30 )
tmap , _ := Transmission . GetTorrentMap ( )
2018-01-11 15:54:03 -08:00
if err != nil {
run = false
if timeoutErr , ok := err . ( net . Error ) ; ok && timeoutErr . Timeout ( ) {
tmap , err = Transmission . GetTorrentMap ( )
if err != nil {
run = true
}
} else {
Transmission = nil
}
}
if run {
for _ , s := range CurrentTorrents {
for _ , se := range s {
for _ , ep := range se {
v , ok := tmap [ ep . Ep [ 0 ] . Meta . Hash ]
if ok {
v . Set ( transmission . SetTorrentArg {
SeedRatioMode : 1 ,
SeedRatioLimit : 1.0 ,
} )
}
2018-01-09 22:52:45 -08:00
}
2018-01-06 22:33:08 -08:00
}
}
}
}
2018-01-06 17:31:50 -08:00
}
func addtorrent ( St SeriesTorrent , torrent * SceneVideoTorrent ) {
_ , ok := St [ torrent . Season ]
if ! ok {
St [ torrent . Season ] = make ( SeasonTorrent , 20 )
}
Ep := St [ torrent . Season ] [ torrent . Episode ]
if Ep == nil {
RES , _ := strconv . Atoi ( args . RES )
St [ torrent . Season ] [ torrent . Episode ] = & EpisodeTorrent {
Tags : make ( map [ string ] int ) ,
Release : make ( map [ string ] int ) ,
Res : scene . Res ( RES ) ,
}
for i , v := range args . RELEASE {
if i + 1 == 0 {
panic ( "You do not exist in a world that I know of" )
}
St [ torrent . Season ] [ torrent . Episode ] . Release [ v ] = i + 1
}
for i , v := range args . NRELEASE {
if i + 1 == 0 {
panic ( "You do not exist in a world that I know of" )
}
2018-01-13 14:03:46 -08:00
St [ torrent . Season ] [ torrent . Episode ] . Release [ v ] = - 1
2018-01-06 17:31:50 -08:00
}
for i , v := range args . TAGS {
if i + 1 == 0 {
panic ( "You do not exist in a world that I know of" )
}
St [ torrent . Season ] [ torrent . Episode ] . Tags [ v ] = i + 1
}
2017-07-16 23:48:06 -07:00
}
2018-01-06 17:31:50 -08:00
St [ torrent . Season ] [ torrent . Episode ] . Add ( torrent )
}
2018-01-09 22:52:45 -08:00
func stopDownloads ( hash [ ] string ) {
2018-01-11 15:54:03 -08:00
var (
run bool = true
tmap transmission . TorrentMap
err error
)
if Transmission != nil {
tmap , err = Transmission . GetTorrentMap ( )
if err != nil {
run = false
if timeoutErr , ok := err . ( net . Error ) ; ok && timeoutErr . Timeout ( ) {
tmap , err = Transmission . GetTorrentMap ( )
if err != nil {
run = true
}
} else {
Transmission = nil
}
}
if run {
thash := make ( [ ] * transmission . Torrent , 0 , len ( hash ) )
for _ , CHash := range hash {
v , ok := tmap [ CHash ]
if ok {
current := scene . Parse ( v . Name )
if CurrentTorrents [ current . Title ] [ current . Season ] [ current . Episode ] . Ep [ 0 ] . Meta . Hash != CHash {
thash = append ( thash , v )
}
}
}
// Removes torrents from transmission that are not selected this time
for _ , torrent := range thash {
torrent . Stop ( )
2018-01-06 17:31:50 -08:00
}
}
2018-01-06 21:25:39 -08:00
}
2018-01-06 17:31:50 -08:00
}
func initialize ( ) {
var (
err error
)
args . PATH , _ = os . Getwd ( )
args . RES = "-1"
2018-01-09 22:52:45 -08:00
args . HOST = "localhost"
2018-01-06 17:31:50 -08:00
arg . MustParse ( & args )
CurrentTorrents = make ( map [ string ] SeriesTorrent , len ( args . Series ) )
for _ , title := range args . Series {
fmt . Println ( title )
CurrentTorrents [ title ] = make ( SeriesTorrent , 10 )
}
unselectedDir , _ = filepath . Abs ( filepath . Join ( args . PATH , "unselected/" ) )
// Load all downloaded torrents
2018-01-09 22:52:45 -08:00
if ! args . NEW {
unselectedFolder , _ := os . Open ( unselectedDir )
defer unselectedFolder . Close ( )
unselectedNames , _ := unselectedFolder . Readdirnames ( 0 )
sort . Strings ( unselectedNames )
for _ , name := range unselectedNames {
if filepath . Ext ( name ) == ".torrent" {
current := process ( filepath . Join ( unselectedDir , name ) )
for _ , title := range args . Series {
if current . Title == title {
addtorrent ( CurrentTorrents [ title ] , current )
break
}
}
2018-01-06 17:31:50 -08:00
}
}
}
2018-01-09 22:52:45 -08:00
username := "lordwelch"
passwd := "hello"
cl := & http . Client {
2018-01-11 15:54:03 -08:00
Transport : & http . Transport {
Dial : ( & net . Dialer {
Timeout : 10 * time . Second ,
} ) . Dial ,
} ,
Timeout : time . Second * 30 ,
2018-01-09 22:52:45 -08:00
}
req , err := http . NewRequest ( "GET" , "http://" + args . HOST + ":9091/transmission/rpc" , nil )
req . SetBasicAuth ( username , passwd )
resp , err := cl . Do ( req )
2018-01-06 17:31:50 -08:00
if err != nil {
2018-01-09 22:52:45 -08:00
fmt . Println ( err )
} else {
resp . Body . Close ( )
Transmission , _ = transmission . New ( transmission . Config {
User : username ,
Password : passwd ,
Address : "http://" + args . HOST + ":9091/transmission/rpc" ,
HTTPClient : cl ,
} )
2018-01-06 17:31:50 -08:00
}
download ( )
2017-06-20 12:25:19 -07:00
}
2017-09-27 13:17:58 -07:00
func process ( torrentFile string ) * SceneVideoTorrent {
2017-06-20 12:25:19 -07:00
var (
2018-01-06 17:31:50 -08:00
mt = new ( MetaTorrent )
vt = new ( SceneVideoTorrent )
2017-06-20 12:25:19 -07:00
)
2018-01-06 17:31:50 -08:00
2017-11-30 20:40:41 -08:00
f , _ := os . OpenFile ( torrentFile , os . O_RDONLY , 755 )
2018-01-06 17:31:50 -08:00
defer f . Close ( )
2017-11-30 20:40:41 -08:00
mt . ReadFile ( f )
2017-06-20 12:25:19 -07:00
vt . Torrent = NewTorrent ( * mt )
2018-01-06 17:31:50 -08:00
vt . Parse ( strings . TrimSuffix ( vt . Name , filepath . Ext ( vt . Name ) ) )
//fmt.Println(vt.Original)
2018-01-09 22:52:45 -08:00
//fmt.Println(vt.Title)
2017-06-20 12:25:19 -07:00
return vt
2017-06-17 02:11:46 -07:00
}