Advertisement
DarthFarious

Script to download Manga from MangaEden

Apr 21st, 2017
722
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. # ///////////////////////////////////////////
  2. #       Author: DarthFarious
  3. #       Dated: 20 April 2017
  4. # -------------------------------------------
  5. # This script will download manga from MangaEden.Com,
  6. # in their respective chapter-wise folders,
  7. # and finally make a archive from the chapter folder
  8. # to read in a CBR/CBZ reader
  9. # -------------------------------------------
  10. # Contact me on Reddit:
  11. # https://www.reddit.com/user/DarthFarious/
  12. # ///////////////////////////////////////////
  13.  
  14. Add-Type -As System.IO.Compression.FileSystem
  15.  
  16. function New-ZipFile {
  17.   #.Synopsis
  18.   #  Create a new zip file, optionally appending to an existing zip...
  19.   [CmdletBinding()]
  20.   param(
  21.     # The path of the zip to create
  22.     [Parameter(Position=0, Mandatory=$true)]
  23.     $ZipFilePath,
  24.  
  25.     # Items that we want to add to the ZipFile
  26.     [Parameter(Position=1, Mandatory=$true, ValueFromPipelineByPropertyName=$true)]
  27.     [Alias("PSPath","Item")]
  28.     [string[]]$InputObject = $Pwd,
  29.  
  30.     # Append to an existing zip file, instead of overwriting it
  31.     [Switch]$Append,
  32.  
  33.     # The compression level (defaults to Optimal):
  34.     #   Optimal - The compression operation should be optimally compressed, even if the operation takes a longer time to complete.
  35.     #   Fastest - The compression operation should complete as quickly as possible, even if the resulting file is not optimally compressed.
  36.     #   NoCompression - No compression should be performed on the file.
  37.     [System.IO.Compression.CompressionLevel]$Compression = "Optimal"
  38.   )
  39.   begin {
  40.     # Make sure the folder already exists
  41.     [string]$File = Split-Path $ZipFilePath -Leaf
  42.     [string]$Folder = $(if($Folder = Split-Path $ZipFilePath) { Resolve-Path $Folder } else { $Pwd })
  43.     $ZipFilePath = Join-Path $Folder $File
  44.     # If they don't want to append, make sure the zip file doesn't already exist.
  45.     if(!$Append) {
  46.       if(Test-Path $ZipFilePath) { Remove-Item $ZipFilePath }
  47.     }
  48.     $Archive = [System.IO.Compression.ZipFile]::Open( $ZipFilePath, "Update" )
  49.   }
  50.   process {
  51.     foreach($path in $InputObject) {
  52.       foreach($item in Resolve-Path $path) {
  53.         # Push-Location so we can use Resolve-Path -Relative
  54.         Push-Location (Split-Path $item)
  55.         # This will get the file, or all the files in the folder (recursively)
  56.         foreach($file in Get-ChildItem $item -Recurse -File -Force | % FullName) {
  57.           # Calculate the relative file path
  58.           $relative = (Resolve-Path $file -Relative).TrimStart(".\")
  59.           # Add the file to the zip
  60.           $null = [System.IO.Compression.ZipFileExtensions]::CreateEntryFromFile($Archive, $file, $relative, $Compression)
  61.         }
  62.         Pop-Location
  63.       }
  64.     }
  65.   }
  66.   end {
  67.     $Archive.Dispose()
  68.     Get-Item $ZipFilePath
  69.   }
  70. }
  71.  
  72.  
  73. function checkUrlExists {
  74.     <#
  75.     .SYNOPSIS
  76.     Return 1 or 0 depending if the input URL exists
  77.    
  78.     .PARAMETER $URL
  79.     This will be a url,
  80.     for eg  "http://www.mangaeden.com/en/en-manga/tegami-bachi/"
  81.  
  82.     .EXAMPLE
  83.     checkUrlExists "http://www.mangaeden.com/en/en-manga/tegami-bachi/"
  84.  
  85.     Output:
  86.     1
  87.  
  88.  
  89.     #>
  90.     param([string]$URL)
  91.  
  92.     $HTTP_Request = [System.Net.WebRequest]::Create($URL)
  93.  
  94.     try
  95.     {
  96.         $HTTP_Response = $HTTP_Request.GetResponse()
  97.         $HTTP_Status = [int]$HTTP_Response.StatusCode
  98.     }
  99.     catch{}
  100.     finally{}
  101.  
  102.     if($HTTP_Status -eq 200)
  103.     {
  104.         return 1
  105.     }
  106.     else
  107.     {
  108.         return 0
  109.     }
  110.  
  111.     if($HTTP_Response)
  112.     {
  113.         $HTTP_Response.Close()
  114.     }
  115.  
  116. }
  117.  
  118.  
  119. $URL_SERIES = Read-Host -Prompt "Enter Mangaeden URL"
  120.  
  121. $SERIES_NAME = $URL_SERIES.Replace("http://www.mangaeden.com/en/en-manga/","")
  122. $SERIES_NAME = $SERIES_NAME.Replace("http://tmp.mangaeden.com/en/en-manga/","")
  123. $SERIES_NAME = $SERIES_NAME.Replace("/","")
  124.  
  125. #This variable will be used later to search for the chapter URLs in getChapterNos function
  126. #Since the URLs will contain a hyphenated name like
  127. #"tegami-bachi"
  128. #and not
  129. #"Tegami Bachi"
  130. #This variable is stored before the name is correctly capitalised.
  131. $url_title =  $SERIES_NAME
  132.  
  133. $SERIES_NAME = $SERIES_NAME.Replace("-"," ")
  134.  
  135.  
  136. "Checking url, please wait..."
  137. if(-Not(checkUrlExists -URL $URL_SERIES) )
  138. {
  139.     "Invalid URL. Try again."
  140.     "Exiting..."
  141.     Start-Sleep 2
  142.     exit
  143. }
  144.  
  145.  
  146. function caseCorrecter {
  147.     <#
  148.     .SYNOPSIS
  149.         This function will return a string with the first letter of each word capitalized.
  150.  
  151.     .PARAMETER $Name
  152.         This represents the argument string
  153.        
  154.     .EXAMPLE
  155.         $str = "abc def ghi"
  156.         $correct = caseCorrecter -Name $str
  157.         $correct
  158.  
  159.         Output of this will be:
  160.         Abc Def Ghi
  161.  
  162.     #>
  163.     param([string]$Name)
  164.     $ogString = $Name
  165.     [string]$nullCheck = "a" #arbitrary non null value
  166.  
  167.     $tempHold = $ogString[0]
  168.  
  169.     #Capitalize the first letter of the string
  170.     $tempHold = $tempHold.ToString().ToUpper()
  171.  
  172.     #$ogStringCased will store the correctly capitalised string
  173.     $ogStringCased = $tempHold
  174.     [int]$arrayPlace = 1
  175.  
  176.  
  177.     while($nullCheck)
  178.     {
  179.         if($ogString[$arrayPlace] -like " ")
  180.         {
  181.             #If the current letter is a space, capitalize the next letter
  182.             $ogStringCased = $ogStringCased + $ogString[$arrayPlace]
  183.             $tempHold = $ogString[$arrayPlace + 1]
  184.             $tempHold = $tempHold.ToString().ToUpper()
  185.             $ogStringCased = $ogStringCased + $tempHold
  186.             $arrayPlace = $arrayPlace + 1
  187.         }
  188.        
  189.         else
  190.         {
  191.             # If the current letter is not a space, just add it to the $ogStringCased
  192.             # string without any modification
  193.             $ogStringCased = $ogStringCased + $ogString[$arrayPlace]
  194.         }
  195.             $arrayPlace = $arrayPlace + 1
  196.             $nullCheck = $ogString[$arrayPlace]
  197.         }
  198.  
  199.     return $ogStringCased
  200. }
  201.  
  202. $SERIES_NAME = caseCorrecter -Name $SERIES_NAME
  203.  
  204. #SET CURRENT FOLDER AS MAIN MANGA FOLDER
  205. $COMICS_PARENT = $pwd
  206.  
  207. "`nEnter range:"
  208. $requested_issue_lower = Read-Host -Prompt "Lower Limit: "
  209. $requested_issue_higher = Read-Host -Prompt "Higher Limit: "
  210.  
  211. function Is-Numeric($value)
  212. {
  213.   #Will return true if the input is numeric
  214.   return $value -match "^[\d\.]+$"
  215. }
  216.  
  217. if(-Not(Is-Numeric $requested_issue_lower) -or -Not(Is-Numeric $requested_issue_higher))
  218. {
  219.   "Chapters are not numbers!"
  220.   "Exiting..."
  221.   Start-Sleep 2
  222.   exit
  223. }
  224.  
  225.  
  226.  
  227. if($requested_issue_lower -gt $requested_issue_higher)
  228. {
  229.   "Input order is wrong!"
  230.   "Swapping..."
  231.   $t = $requested_issue_lower
  232.   $requested_issue_lower = $requested_issue_higher
  233.   $requested_issue_higher = $t
  234. }
  235.  
  236.  
  237.  
  238. function getChapterNos {
  239.  
  240.     <#
  241.     .SYNOPSIS
  242.     Will return a string array of the chapter numbers.
  243.  
  244.     .PARAMETER $URL
  245.     The url to the main page of the manga
  246.     "http://www.mangaeden.com/en/en-manga/super-secret/"
  247.  
  248.     .PARAMETER $url_title
  249.     The name of the series as it appears in the url
  250.     "super-secret"
  251.     and
  252.     NOT "Super Secret"
  253.  
  254.     .EXAMPLE
  255.     getChapterNos -URL "http://www.mangaeden.com/en/en-manga/super-secret/" -url-title "super-secret'
  256.  
  257.     #>
  258.  
  259.     param([string]$URL,[string]$url_title)
  260.  
  261.     $eden =Invoke-WebRequest -Uri "$URL"
  262.     $links = ($eden.Content).Split("`n")
  263.     $nos =""
  264.    
  265.     foreach($line in $links)
  266.     {
  267.  
  268.     if($line.Contains("en-manga/$url_title/") -and $line.Contains("<a") -and (-Not($line.Contains("eden"))))
  269.         {
  270.           $number =$line.Substring(0,$line.LastIndexOf("/"))
  271.           $number = $number.Replace("<a href=`"/en/en-manga/$url_title/","").Replace("/1","")
  272.           $nos = $nos + $number+"`n"
  273.         }
  274.     }
  275.    
  276.     $nos = $nos -split "`n"
  277.     [array]::Reverse($nos)
  278.  
  279.     #Removing the first line
  280.     $nos = $nos[1..($nos.Length-1)]
  281.  
  282.     return $nos
  283. }
  284.  
  285.  
  286.  
  287. $chapterNos = getChapterNos -URL $URL_SERIES -url_title $url_title
  288.  
  289. $i = 0
  290. #$chapterNos contains all the existing chapter numbers that the website has.
  291. #The while loop is used to find the index of the requested chapter numbers
  292. while($chapterNos[$i])
  293. {
  294.     if($chapterNos[$i] -eq $requested_issue_lower)
  295.     {
  296.       $lowIndex = $i
  297.       "Lower limit $requested_issue_lower exists!"
  298.     }
  299.     if($chapterNos[$i] -eq $requested_issue_higher)
  300.     {
  301.       $highIndex = $i
  302.       "Higher limit $requested_issue_higher exists!"
  303.     }
  304.     $i++
  305. }
  306.  
  307.  
  308. if(($lowIndex -eq $null) -or ($highIndex -eq $null))
  309. {
  310.   "Requested chapters do not exist!"
  311.   "Exiting..."
  312.   Start-Sleep 2
  313.   exit
  314. }
  315.  
  316.  
  317.  
  318.  
  319. function getImageLinks {
  320.    
  321.     <#
  322.     .SYNOPSIS
  323.     This function will return a string array containing all the urls of the individual pages in the chapter
  324.  
  325.     .DESCRIPTION
  326.     The first page of the manga contains the direct imagelinks to the rest of the pages.
  327.     The function will first obtain that line, and then after performing string operations,
  328.     it will return a array of strings which are the direct URLs to the pages.
  329.    
  330.     All these are stored on one line in the source code, ie the line which starts with
  331.     "var pages"
  332.  
  333.  
  334.     .PARAMETER $ChapterURL
  335.     The url of the first page of a chapter
  336.     "http://www.mangaeden.com/en/en-manga/super-secret/1/1/"
  337.  
  338.     .EXAMPLE
  339.     getImageLinks -ChapterURL "http://www.mangaeden.com/en/en-manga/super-secret/1/1/"
  340.  
  341.     #>
  342.  
  343.     param([string]$ChapterURL)
  344.    
  345.     $Chapter = Invoke-WebRequest -Uri $ChapterURL
  346.     $links = ($Chapter.Content).Split("`n")
  347.     $imageLinks = ""
  348.     foreach($line in $links)
  349.     {
  350.         if($line.Contains("var pages"))
  351.         #We need only the line which contains the URLs to the images,
  352.         #hence break is used, and the line is stored in $PARA
  353.         {
  354.         $PARA = $line
  355.         break
  356.         }
  357.     }
  358.  
  359.  
  360.     #This line trims $PARA so that the content before '{"fs"' which is unneeded gets removed.
  361.     $PARA = $PARA.Substring($PARA.IndexOf('{"fs"'))
  362.    
  363.     #Now, all the lines of $PARA start will the direct URL
  364.     # ie "//cdn.mangaeden.com/mangasimg/a4/a401ad23155480090504fc6a226a0acc05ff945a4cede2e1918b8d82.png ..."
  365.     $PARA = $PARA.Replace('{"fs": "',"`n")
  366.    
  367.     #$PARA is now a string array, so now we can use a foreach loop to obtain the url from each line
  368.     $PARA = $PARA.Split("`n")
  369.    
  370.  
  371.     foreach($line in $PARA)
  372.     {
  373.        if($line.Contains('"'))
  374.        {
  375.          #The required URL is only till before the occurence of '"'
  376.          $singlelink = $line.Substring(0,$line.IndexOf('"'))
  377.          $imageLinks = $imageLinks + "http:" + $singlelink + "`n"
  378.        }
  379.     }
  380.  
  381.     $imageLinks = $imageLinks -split "`n"
  382.     return $imageLinks
  383. }
  384.  
  385.  
  386. $SERIES_FOLDER_PATH = "$COMICS_PARENT" + "\" + "$SERIES_NAME"
  387.  
  388. if( -Not(Test-Path $SERIES_FOLDER_PATH))
  389. {
  390.     New-Item -Path "$SERIES_FOLDER_PATH" -ItemType Directory | Out-Null
  391.     "`n#################################"
  392.     "`n$SERIES_NAME folder didnt exist, it has been created"
  393. }
  394.  
  395.  
  396.  
  397.  
  398. $chapterID = $lowIndex
  399. while($chapterID -le $highIndex)
  400. {
  401.     Set-Location $SERIES_FOLDER_PATH
  402.  
  403.     $chapterNumber = $chapterNos[$chapterID]
  404.     $URL_CHAPTER = $URL_SERIES + $chapterNumber + "/1/"
  405.    
  406.     $imageURLs = getImageLinks -ChapterURL $URL_CHAPTER
  407.  
  408.     #The $chapterNumberCorrect variable exists since Windows puts 56.4 before 56
  409.     #So to preserve the correct reading order
  410.     #I have put a ".0" after the integer chapters
  411.     # and stored that value to $chapterNumberCorrect
  412.     if($chapterNumber.Contains("."))
  413.     {
  414.       $chapterNumberCorrect = "$chapterNumber"
  415.     }
  416.     else
  417.     {
  418.       $chapterNumberCorrect = "$chapterNumber.0"
  419.     }
  420.  
  421.  
  422.     $CHAPTER_FOLDER_PATH = "$SERIES_FOLDER_PATH" + "\" + "Chapter " + "$chapterNumberCorrect"
  423.    
  424.    
  425.     if(-Not(Test-Path $CHAPTER_FOLDER_PATH))
  426.     {
  427.       New-Item -Path "$CHAPTER_FOLDER_PATH" -ItemType Directory | Out-Null
  428.       "`n#################################"
  429.     # "`nChapter $chapterNumber folder didnt exist, it has been created"
  430.       "`nChapter $chapterNumberCorrect folder didnt exist, it has been created"
  431.     }
  432.  
  433.     Set-Location $CHAPTER_FOLDER_PATH
  434.    
  435.     "`n#################################"
  436.     "`nDownloading Chapter $chapterNumberCorrect `n"
  437.    
  438.     #DOWNLOAD LOOP FOR SINGLE CHAPTER
  439.     $pageID =0
  440.     while($imageURLs[$pageID])
  441.     {
  442.          #[int] is used since, these variabls are used as strings in the following lines
  443.          #without [int] there might be problems where
  444.          #insead of 1+1=2, we might get 1+1=11
  445.          [int]$pageNo = [int]$pageID + 1
  446.        
  447.        
  448.          #These if-else make sure that the reader correctly arranges the pages
  449.          #Since some readers put the order as
  450.          # 1 10 11 12 ... 19 2 20 21 22
  451.          if($pageNo -ge 1 -and $pageNo -lt 10)
  452.          {
  453.            $pageNoCorrect = "00" + $pageNo
  454.          }
  455.          if($pageNo -ge 10 -and $pageNo -lt 100)
  456.          {
  457.            $pageNoCorrect = "0" + $pageNo
  458.          }
  459.          if($pageNo -ge 100 -and $pageNo -lt 1000)
  460.          {
  461.            $pageNoCorrect = $pageNo
  462.          }
  463.  
  464.         $PAGE_URL = $imageURLs[$pageID]
  465.         $PAGE_PATH = $CHAPTER_FOLDER_PATH + "\" + $pageNoCorrect + ".jpg"
  466.  
  467.  
  468.         if( Test-Path $PAGE_PATH)
  469.         {
  470.           "File " + $pageNoCorrect + " exists! Skipping file..."
  471.         }
  472.         else
  473.         {
  474.           $web = New-Object System.Net.WebClient
  475.          "Downloading Page $pageNo"
  476.           $web.DownloadFile($PAGE_URL,$PAGE_PATH)
  477.         }
  478.  
  479.         #$pageID doesn't need a increment since $pageNO is already one more than $pageID
  480.         $pageID =$pageNo
  481.  
  482.  
  483.  
  484.     }
  485.  
  486.     "`nChapter $chapterNumberCorrect is downloaded."
  487.  
  488.    
  489.     #$zipName is the filename of the zip file that will be created for each folder
  490.     #This variable can be customised to suit the user's needs
  491.     #Currently it is set as
  492.     #Chapter Number - Series Name - Chapter Number
  493.         $zipName = "$chapterNumberCorrect - $SERIES_NAME - Chapter $chapterNumberCorrect"
  494.  
  495.  
  496.     $chapterZipPath = $SERIES_FOLDER_PATH + "\" + $zipName + ".zip"
  497.  
  498.     if( -Not(Test-Path $chapterZipPath))
  499.     {
  500.       "`nCreating $zipName.zip"
  501.       New-ZipFile -ZipFilePath $chapterZipPath -InputObject $CHAPTER_FOLDER_PATH | Out-Null
  502.     }
  503.     else
  504.     {
  505.       "$zipName.zip exists!"
  506.     }
  507.  
  508.  
  509. $chapterID++
  510. }
  511.  
  512. Read-Host -Prompt "Press Enter to exit."
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement