Пример #1
0
def generate_html(output_dir='.', doujinshi_obj=None):
    image_html = ''

    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(output_dir, format_filename('%s-%s' % (doujinshi_obj.id,
                                                                            str(doujinshi_obj.name[:200]))))
    else:
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    for image in file_list:
        if not os.path.splitext(image)[1] in ('.jpg', '.png'):
            continue

        image_html += '<img src="{0}" class="image-item"/>\n'\
            .format(image)

    html = readfile('viewer/index.html')
    css = readfile('viewer/styles.css')
    js = readfile('viewer/scripts.js')

    if doujinshi_obj is not None:
        title = doujinshi_obj.name
    else:
        title = 'nHentai HTML Viewer'

    data = html.format(TITLE=title, IMAGES=image_html, SCRIPTS=js, STYLES=css)
    with open(os.path.join(doujinshi_dir, 'index.html'), 'w') as f:
        f.write(data)

    logger.log(15, 'HTML Viewer has been write to \'{0}\''.format(os.path.join(doujinshi_dir, 'index.html')))
Пример #2
0
def generate_cbz(output_dir='.', doujinshi_obj=None):
    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(
            output_dir,
            format_filename('%s-%s' %
                            (doujinshi_obj.id, str(doujinshi_obj.name[:200]))))
        cbz_filename = os.path.join(
            output_dir,
            format_filename('%s-%s.cbz' %
                            (doujinshi_obj.id, str(doujinshi_obj.name[:200]))))
    else:
        cbz_filename = './doujinshi.cbz'
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    with zipfile.ZipFile(cbz_filename, 'w') as cbz_pf:
        for image in file_list:
            image_path = os.path.join(doujinshi_dir, image)
            cbz_pf.write(image_path, image)

    shutil.rmtree(doujinshi_dir, ignore_errors=True)
    logger.log(
        15,
        'Comic Book CBZ file has been write to \'{0}\''.format(doujinshi_dir))
Пример #3
0
def generate_pdf(output_dir='.', doujinshi_obj=None, rm_origin_dir=False):
    """Write images to a PDF file using img2pdf."""
    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(output_dir, doujinshi_obj.filename)
        pdf_filename = os.path.join(os.path.join(doujinshi_dir, '..'),
                                    '{}.pdf'.format(doujinshi_obj.filename))
    else:
        pdf_filename = './doujinshi.pdf'
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    logger.info('Writing PDF file to path: {}'.format(pdf_filename))
    with open(pdf_filename, 'wb') as pdf_f:
        full_path_list = ([
            os.path.join(doujinshi_dir, image) for image in file_list
        ])
        pdf_f.write(img2pdf.convert(full_path_list))

    if rm_origin_dir:
        shutil.rmtree(doujinshi_dir, ignore_errors=True)

    logger.log(15,
               'PDF file has been written to \'{0}\''.format(doujinshi_dir))
Пример #4
0
def doujinshi_parser(id_):
    if not isinstance(id_, (int,)) and (isinstance(id_, (str,)) and not id_.isdigit()):
        raise Exception('Doujinshi id({0}) is not valid'.format(id_))

    id_ = int(id_)
    logger.log(15, 'Fetching doujinshi information of id {0}'.format(id_))
    doujinshi = dict()
    doujinshi['id'] = id_
    url = '{0}/{1}'.format(constant.DETAIL_URL, id_)

    try:
        response = request('get', url).json()
    except Exception as e:
        logger.critical(str(e))
        exit(1)

    doujinshi['name'] = str(response['title']['english'].encode('utf-8'))[2:]
    doujinshi['subtitle'] = response['title']['japanese']
    doujinshi['img_id'] = response['media_id']
    doujinshi['ext'] = ''.join(map(lambda s: s['t'], response['images']['pages']))
    doujinshi['pages'] = len(response['images']['pages'])

    # gain information of the doujinshi
    needed_fields = ['character', 'artist', 'language']
    for tag in response['tags']:
        tag_type = tag['type']
        if tag_type in needed_fields:
            if tag_type not in doujinshi:
                doujinshi[tag_type] = tag['name']
            else:
                doujinshi[tag_type] += tag['name']

    return doujinshi
Пример #5
0
def main():
    banner()
    options = cmd_parser()

    doujinshi_ids = []
    doujinshi_list = []

    if options.keyword:
        doujinshis = search_parser(options.keyword, options.page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)
    else:
        doujinshi_ids = options.ids

    if doujinshi_ids:
        for id in doujinshi_ids:
            doujinshi_info = doujinshi_parser(id)
            doujinshi_list.append(Doujinshi(**doujinshi_info))
    else:
        exit(0)

    if options.is_download:
        downloader = Downloader(path=options.saved_path,
                                thread=options.threads,
                                timeout=options.timeout)
        for doujinshi in doujinshi_list:
            doujinshi.downloader = downloader
            doujinshi.download()
    else:
        map(lambda doujinshi: doujinshi.show(), doujinshi_list)

    logger.log(15, u'🍺 All done.')
Пример #6
0
def generate_cbz(output_dir='.',
                 doujinshi_obj=None,
                 rm_origin_dir=False,
                 write_comic_info=False):
    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(output_dir, doujinshi_obj.filename)
        if write_comic_info:
            serialize_comicxml(doujinshi_obj, doujinshi_dir)
        cbz_filename = os.path.join(os.path.join(doujinshi_dir, '..'),
                                    '{}.cbz'.format(doujinshi_obj.filename))
    else:
        cbz_filename = './doujinshi.cbz'
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    logger.info('Writing CBZ file to path: {}'.format(cbz_filename))
    with zipfile.ZipFile(cbz_filename, 'w') as cbz_pf:
        for image in file_list:
            image_path = os.path.join(doujinshi_dir, image)
            cbz_pf.write(image_path, image)

    if rm_origin_dir:
        shutil.rmtree(doujinshi_dir, ignore_errors=True)

    logger.log(
        15, 'Comic Book CBZ file has been written to \'{0}\''.format(
            doujinshi_dir))
Пример #7
0
def generate_main_html(output_dir='./'):
    """
    Generate a main html to show all the contain doujinshi.
    With a link to their `index.html`.
    Default output folder will be the CLI path.
    """

    image_html = ''

    main = readfile('viewer/main.html')
    css = readfile('viewer/main.css')
    js = readfile('viewer/main.js')

    element = '\n\
            <div class="gallery-favorite">\n\
                <div class="gallery">\n\
                    <a href="./{FOLDER}/index.html" class="cover" style="padding:0 0 141.6% 0"><img\n\
                            src="./{FOLDER}/{IMAGE}" />\n\
                        <div class="caption">{TITLE}</div>\n\
                    </a>\n\
                </div>\n\
            </div>\n'

    os.chdir(output_dir)
    doujinshi_dirs = next(os.walk('.'))[1]

    for folder in doujinshi_dirs:
        files = os.listdir(folder)
        files.sort()

        if 'index.html' in files:
            logger.info('Add doujinshi \'{}\''.format(folder))
        else:
            continue

        image = files[0]  # 001.jpg or 001.png
        if folder is not None:
            title = folder.replace('_', ' ')
        else:
            title = 'nHentai HTML Viewer'

        image_html += element.format(FOLDER=folder, IMAGE=image, TITLE=title)
    if image_html == '':
        logger.warning('No index.html found, --gen-main paused.')
        return
    try:
        data = main.format(STYLES=css, SCRIPTS=js, PICTURE=image_html)
        if sys.version_info < (3, 0):
            with open('./main.html', 'w') as f:
                f.write(data)
        else:
            with open('./main.html', 'wb') as f:
                f.write(data.encode('utf-8'))
        shutil.copy(os.path.dirname(__file__) + '/viewer/logo.png', './')
        set_js_database()
        logger.log(
            15, 'Main Viewer has been written to \'{0}main.html\''.format(
                output_dir))
    except Exception as e:
        logger.warning('Writing Main Viewer failed ({})'.format(str(e)))
Пример #8
0
def doujinshi_parser(id_):
    if not isinstance(id_, (int,)) and (isinstance(id_, (str,)) and not id_.isdigit()):
        raise Exception('Doujinshi id({0}) is not valid'.format(id_))

    id_ = int(id_)
    logger.log(15, 'Fetching doujinshi information of id {0}'.format(id_))
    doujinshi = dict()
    doujinshi['id'] = id_
    url = '{0}/{1}/'.format(constant.DETAIL_URL, id_)

    try:
        response = request('get', url).content
    except Exception as e:
        logger.critical(str(e))
        raise SystemExit

    html = BeautifulSoup(response, 'html.parser')
    doujinshi_info = html.find('div', attrs={'id': 'info'})

    title = doujinshi_info.find('h1').text
    subtitle = doujinshi_info.find('h2')

    doujinshi['name'] = title
    doujinshi['subtitle'] = subtitle.text if subtitle else ''

    doujinshi_cover = html.find('div', attrs={'id': 'cover'})
    img_id = re.search('/galleries/([\d]+)/cover\.(jpg|png)$', doujinshi_cover.a.img.attrs['data-src'])

    ext = []
    for i in html.find_all('div', attrs={'class': 'thumb-container'}):
        _, ext_name = os.path.basename(i.img.attrs['data-src']).rsplit('.', 1)
        ext.append(ext_name)

    if not img_id:
        logger.critical('Tried yo get image id failed')
        exit(1)

    doujinshi['img_id'] = img_id.group(1)
    doujinshi['ext'] = ext

    pages = 0
    for _ in doujinshi_info.find_all('div', class_=''):
        pages = re.search('([\d]+) pages', _.text)
        if pages:
            pages = pages.group(1)
            break
    doujinshi['pages'] = int(pages)

    # gain information of the doujinshi
    information_fields = doujinshi_info.find_all('div', attrs={'class': 'field-name'})
    needed_fields = ['Characters', 'Artists', 'Language', 'Tags']
    for field in information_fields:
        field_name = field.contents[0].strip().strip(':')
        if field_name in needed_fields:
            data = [sub_field.contents[0].strip() for sub_field in
                    field.find_all('a', attrs={'class': 'tag'})]
            doujinshi[field_name.lower()] = ', '.join(data)

    return doujinshi
Пример #9
0
def main():
    banner()
    logger.info('Using mirror: {0}'.format(BASE_URL))
    options = cmd_parser()

    doujinshi_ids = []
    doujinshi_list = []

    if options.login:
        username, password = options.login.split(':', 1)
        logger.info('Logging in to nhentai using credential pair \'%s:%s\'' %
                    (username, '*' * len(password)))
        login(username, password)

        if options.is_download:
            for doujinshi_info in login_parser():
                doujinshi_list.append(Doujinshi(**doujinshi_info))

    if options.tag:
        doujinshis = tag_parser(options.tag, max_page=options.max_page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)

    if options.keyword:
        doujinshis = search_parser(options.keyword, options.page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)

    if not doujinshi_ids:
        doujinshi_ids = options.id

    if doujinshi_ids:
        for id_ in doujinshi_ids:
            doujinshi_info = doujinshi_parser(id_)
            doujinshi_list.append(Doujinshi(**doujinshi_info))

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                thread=options.threads,
                                timeout=options.timeout)

        for doujinshi in doujinshi_list:
            doujinshi.downloader = downloader
            doujinshi.download()
            if not options.is_nohtml and not options.is_cbz:
                generate_html(options.output_dir, doujinshi)
            elif options.is_cbz:
                generate_cbz(options.output_dir, doujinshi,
                             options.rm_origin_dir)

        if not platform.system() == 'Windows':
            logger.log(15, '🍻 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]
Пример #10
0
def doujinshi_parser(id_):
    if not isinstance(id_, (int,)) and (isinstance(id_, (str,)) and not id_.isdigit()):
        raise Exception('Doujinshi id({0}) is not valid'.format(id_))

    id_ = int(id_)
    logger.log(15, 'Fetching doujinshi information of id {0}'.format(id_))
    doujinshi = dict()
    doujinshi['id'] = id_
    url = '{0}/{1}/'.format(constant.DETAIL_URL, id_)

    try:
        response = request('get', url).content
    except Exception as e:
        logger.critical(str(e))
        raise SystemExit

    html = BeautifulSoup(response, 'html.parser')
    doujinshi_info = html.find('div', attrs={'id': 'info'})

    title = doujinshi_info.find('h1').text
    subtitle = doujinshi_info.find('h2')

    doujinshi['name'] = title
    doujinshi['subtitle'] = subtitle.text if subtitle else ''

    doujinshi_cover = html.find('div', attrs={'id': 'cover'})
    img_id = re.search('/galleries/([\d]+)/cover\.(jpg|png)$', doujinshi_cover.a.img.attrs['data-src'])

    ext = []
    for i in html.find_all('div', attrs={'class': 'thumb-container'}):
        _, ext_name = os.path.basename(i.img.attrs['data-src']).rsplit('.', 1)
        ext.append(ext_name)

    if not img_id:
        logger.critical('Tried yo get image id failed')
        exit(1)

    doujinshi['img_id'] = img_id.group(1)
    doujinshi['ext'] = ext

    pages = 0
    for _ in doujinshi_info.find_all('div', class_=''):
        pages = re.search('([\d]+) pages', _.text)
        if pages:
            pages = pages.group(1)
            break
    doujinshi['pages'] = int(pages)

    # gain information of the doujinshi
    information_fields = doujinshi_info.find_all('div', attrs={'class': 'field-name'})
    needed_fields = ['Characters', 'Artists', 'Language', 'Tags']
    for field in information_fields:
        field_name = field.contents[0].strip().strip(':')
        if field_name in needed_fields:
            data = [sub_field.contents[0].strip() for sub_field in
                    field.find_all('a', attrs={'class': 'tag'})]
            doujinshi[field_name.lower()] = ', '.join(data)

    return doujinshi
Пример #11
0
 def _download_callback(self, request, result):
     result, data = result
     if result == 0:
         logger.warning('fatal errors occurred, ignored')
         # exit(1)
     elif result == -1:
         logger.warning('url {} return status code 404'.format(data))
     else:
         logger.log(15, '{0} downloaded successfully'.format(data))
Пример #12
0
 def _download_callback(self, request, result):
     result, data = result
     if result == 0:
         logger.critical('fatal errors occurred, quit.')
         exit(1)
     elif result == -1:
         logger.warning('url {} return status code 404'.format(data))
     else:
         logger.log(15, '{0} download successfully'.format(data))
Пример #13
0
def main():
    banner()
    logger.info('Using mirror: {0}'.format(BASE_URL))
    options = cmd_parser()

    doujinshi_ids = []
    doujinshi_list = []

    if options.login:
        username, password = options.login.split(':', 1)
        logger.info('Logging in to nhentai using credential pair \'%s:%s\'' % (username, '*' * len(password)))
        login(username, password)

        if options.is_download:
            for doujinshi_info in login_parser():
                doujinshi_list.append(Doujinshi(**doujinshi_info))

    if options.tag:
        doujinshis = tag_parser(options.tag, max_page=options.max_page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)

    if options.keyword:
        doujinshis = search_parser(options.keyword, options.page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)

    if not doujinshi_ids:
        doujinshi_ids = options.id

    if doujinshi_ids:
        for id_ in doujinshi_ids:
            doujinshi_info = doujinshi_parser(id_)
            doujinshi_list.append(Doujinshi(**doujinshi_info))

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                thread=options.threads, timeout=options.timeout)

        for doujinshi in doujinshi_list:
            doujinshi.downloader = downloader
            doujinshi.download()
            if not options.is_nohtml and not options.is_cbz:
                generate_html(options.output_dir, doujinshi)
            elif options.is_cbz:
                generate_cbz(options.output_dir, doujinshi, options.rm_origin_dir)

        if not platform.system() == 'Windows':
            logger.log(15, '🍻 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]
Пример #14
0
def main():
    banner()
    logger.info('Using mirror: {0}'.format(BASE_URL))
    options = cmd_parser()

    doujinshi_ids = []
    doujinshi_list = []

    if options.favorites:
        if not options.is_download:
            logger.warning('You do not specify --download option')

        doujinshi_ids = favorites_parser()

    elif options.tag:
        doujinshis = tag_parser(options.tag, max_page=options.max_page)
        print_doujinshi(doujinshis)
        if options.is_download and doujinshis:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)

    elif options.keyword:
        doujinshis = search_parser(options.keyword, options.page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)

    elif not doujinshi_ids:
        doujinshi_ids = options.id

    if doujinshi_ids:
        for id_ in doujinshi_ids:
            if options.delay:
                time.sleep(options.delay)
            doujinshi_info = doujinshi_parser(id_)
            doujinshi_list.append(Doujinshi(name_format=options.name_format, path=options.output_dir, **doujinshi_info))

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                thread=options.threads, timeout=options.timeout, delay=options.delay)

        for doujinshi in doujinshi_list:
            doujinshi.downloader = downloader
            doujinshi.download()
            if not options.is_nohtml and not options.is_cbz:
                generate_html(options.output_dir, doujinshi)
            elif options.is_cbz:
                generate_cbz(options.output_dir, doujinshi, options.rm_origin_dir)

        if not platform.system() == 'Windows':
            logger.log(15, '🍻 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]
Пример #15
0
def generate_html(output_dir='.', doujinshi_obj=None, template='default'):
    image_html = ''

    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(output_dir, doujinshi_obj.filename)
    else:
        doujinshi_dir = '.'

    if not os.path.exists(doujinshi_dir):
        logger.warning(
            'Path \'{0}\' does not exist, creating.'.format(doujinshi_dir))
        try:
            os.makedirs(doujinshi_dir)
        except EnvironmentError as e:
            logger.critical('{0}'.format(str(e)))

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    for image in file_list:
        if not os.path.splitext(image)[1] in ('.jpg', '.png'):
            continue

        image_html += '<img src="{0}" class="image-item"/>\n'\
            .format(image)
    html = readfile('viewer/{}/index.html'.format(template))
    css = readfile('viewer/{}/styles.css'.format(template))
    js = readfile('viewer/{}/scripts.js'.format(template))

    if doujinshi_obj is not None:
        serialize_json(doujinshi_obj, doujinshi_dir)
        name = doujinshi_obj.name
        if sys.version_info < (3, 0):
            name = doujinshi_obj.name.encode('utf-8')
    else:
        name = {'title': 'nHentai HTML Viewer'}

    data = html.format(TITLE=name, IMAGES=image_html, SCRIPTS=js, STYLES=css)
    try:
        if sys.version_info < (3, 0):
            with open(os.path.join(doujinshi_dir, 'index.html'), 'w') as f:
                f.write(data)
        else:
            with open(os.path.join(doujinshi_dir, 'index.html'), 'wb') as f:
                f.write(data.encode('utf-8'))

        logger.log(
            15, 'HTML Viewer has been written to \'{0}\''.format(
                os.path.join(doujinshi_dir, 'index.html')))
    except Exception as e:
        logger.warning('Writing HTML Viewer failed ({})'.format(str(e)))
Пример #16
0
 def _download_callback(self, result):
     result, data = result
     if result == 0:
         logger.warning('fatal errors occurred, ignored')
         # exit(1)
     elif result == -1:
         logger.warning('url {} return status code 404'.format(data))
     elif result == -2:
         logger.warning('Ctrl-C pressed, exiting sub processes ...')
     elif result == -3:
         # workers wont be run, just pass
         pass
     else:
         logger.log(15, '{0} downloaded successfully'.format(data))
Пример #17
0
def __api_suspended_doujinshi_parser(id_):
    if not isinstance(id_,
                      (int, )) and (isinstance(id_,
                                               (str, )) and not id_.isdigit()):
        raise Exception('Doujinshi id({0}) is not valid'.format(id_))

    id_ = int(id_)
    logger.log(15, 'Fetching information of doujinshi id {0}'.format(id_))
    doujinshi = dict()
    doujinshi['id'] = id_
    url = '{0}/{1}'.format(constant.DETAIL_URL, id_)
    i = 0
    while 5 > i:
        try:
            response = request('get', url).json()
        except Exception as e:
            i += 1
            if not i < 5:
                logger.critical(str(e))
                exit(1)
            continue
        break

    doujinshi['name'] = response['title']['english']
    doujinshi['subtitle'] = response['title']['japanese']
    doujinshi['img_id'] = response['media_id']
    doujinshi['ext'] = ''.join([i['t'] for i in response['images']['pages']])
    doujinshi['pages'] = len(response['images']['pages'])

    # gain information of the doujinshi
    needed_fields = [
        'character', 'artist', 'language', 'tag', 'parody', 'group', 'category'
    ]
    for tag in response['tags']:
        tag_type = tag['type']
        if tag_type in needed_fields:
            if tag_type == 'tag':
                if tag_type not in doujinshi:
                    doujinshi[tag_type] = {}

                tag['name'] = tag['name'].replace(' ', '-')
                tag['name'] = tag['name'].lower()
                doujinshi[tag_type][tag['name']] = tag['id']
            elif tag_type not in doujinshi:
                doujinshi[tag_type] = tag['name']
            else:
                doujinshi[tag_type] += ', ' + tag['name']

    return doujinshi
Пример #18
0
def __api_suspended_doujinshi_parser(id_):
    if not isinstance(id_, (int,)) and (isinstance(id_, (str,)) and not id_.isdigit()):
        raise Exception('Doujinshi id({0}) is not valid'.format(id_))

    id_ = int(id_)
    logger.log(15, 'Fetching information of doujinshi id {0}'.format(id_))
    doujinshi = dict()
    doujinshi['id'] = id_
    url = '{0}/{1}'.format(constant.DETAIL_URL, id_)
    i = 0
    while 5 > i:
        try:
            response = request('get', url).json()
        except Exception as e:
            i += 1
            if not i < 5:
                logger.critical(str(e))
                exit(1)
            continue
        break

    doujinshi['name'] = response['title']['english']
    doujinshi['subtitle'] = response['title']['japanese']
    doujinshi['img_id'] = response['media_id']
    doujinshi['ext'] = ''.join(map(lambda s: s['t'], response['images']['pages']))
    doujinshi['pages'] = len(response['images']['pages'])

    # gain information of the doujinshi
    needed_fields = ['character', 'artist', 'language', 'tag']
    for tag in response['tags']:
        tag_type = tag['type']
        if tag_type in needed_fields:
            if tag_type == 'tag':
                if tag_type not in doujinshi:
                    doujinshi[tag_type] = {}

                tag['name'] = tag['name'].replace(' ', '-')
                tag['name'] = tag['name'].lower()
                doujinshi[tag_type][tag['name']] = tag['id']
            elif tag_type not in doujinshi:
                doujinshi[tag_type] = tag['name']
            else:
                doujinshi[tag_type] += ', ' + tag['name']

    return doujinshi
Пример #19
0
def generate_html(output_dir='.', doujinshi_obj=None):
    image_html = ''

    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(
            output_dir,
            format_filename('%s-%s' % (doujinshi_obj.id, doujinshi_obj.name)))
    else:
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    for image in file_list:
        if not os.path.splitext(image)[1] in ('.jpg', '.png'):
            continue

        image_html += '<img src="{0}" class="image-item"/>\n'\
            .format(image)

    html = readfile('viewer/index.html')
    css = readfile('viewer/styles.css')
    js = readfile('viewer/scripts.js')

    if doujinshi_obj is not None:
        title = doujinshi_obj.name
        if sys.version_info < (3, 0):
            title = title.encode('utf-8')
    else:
        title = 'nHentai HTML Viewer'

    data = html.format(TITLE=title, IMAGES=image_html, SCRIPTS=js, STYLES=css)
    try:
        if sys.version_info < (3, 0):
            with open(os.path.join(doujinshi_dir, 'index.html'), 'w') as f:
                f.write(data)
        else:
            with open(os.path.join(doujinshi_dir, 'index.html'), 'wb') as f:
                f.write(data.encode('utf-8'))

        logger.log(
            15, 'HTML Viewer has been write to \'{0}\''.format(
                os.path.join(doujinshi_dir, 'index.html')))
    except Exception as e:
        logger.warning('Writen HTML Viewer failed ({})'.format(str(e)))
Пример #20
0
def generate_html(output_dir='.', doujinshi_obj=None):
    image_html = ''
    previous = ''

    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(
            output_dir,
            format_filename('%s-%s' %
                            (doujinshi_obj.id, doujinshi_obj.name[:200])))
    else:
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    for index, image in enumerate(file_list):
        if not os.path.splitext(image)[1] in ('.jpg', '.png'):
            continue

        try:
            next_ = file_list[file_list.index(image) + 1]
        except IndexError:
            next_ = ''

        image_html += '<img src="{0}" class="image-item {1}" attr-prev="{2}" attr-next="{3}">\n'\
            .format(image, 'current' if index == 0 else '', previous, next_)
        previous = image

    with open(os.path.join(os.path.dirname(__file__), 'doujinshi.html'),
              'r') as template:
        html = template.read()

    if doujinshi_obj is not None:
        title = doujinshi_obj.name
    else:
        title = 'nHentai HTML Viewer'

    data = html.format(TITLE=title, IMAGES=image_html)
    with open(os.path.join(doujinshi_dir, 'index.html'), 'w') as f:
        f.write(data)

    logger.log(
        15, 'HTML Viewer has been write to \'{0}\''.format(
            os.path.join(doujinshi_dir, 'index.html')))
Пример #21
0
def generate_html(output_dir='.', doujinshi_obj=None):
    image_html = ''

    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(output_dir, doujinshi_obj.filename)
    else:
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list = list(filter(lambda x:x.split('.')[0].isdigit(), file_list)) # remove non-digit file names
    file_list.sort(key = lambda x: int(x.split('.')[0])) # sort by num

    for image in file_list:
        if not os.path.splitext(image)[1] in ('.jpg', '.png'):
            continue

        image_html += '<img src="{0}" class="image-item"/>\n'\
            .format(image)
    html = readfile('viewer/index.html')
    css = readfile('viewer/styles.css')
    js = readfile('viewer/scripts.js')

    if doujinshi_obj is not None:
        serialize_json(doujinshi_obj, doujinshi_dir)
        name = doujinshi_obj.name
        if sys.version_info < (3, 0):
            name = doujinshi_obj.name.encode('utf-8')
    else:
        name = {'title': 'nHentai HTML Viewer'}

    data = html.format(TITLE=name, IMAGES=image_html, SCRIPTS=js, STYLES=css)
    try:
        if sys.version_info < (3, 0):
            with open(os.path.join(doujinshi_dir, 'index.html'), 'w') as f:
                f.write(data)
        else:
            with open(os.path.join(doujinshi_dir, 'index.html'), 'wb') as f:
                f.write(data.encode('utf-8'))

        logger.log(15, 'HTML Viewer has been written to \'{0}\''.format(os.path.join(doujinshi_dir, 'index.html')))
    except Exception as e:
        logger.warning('Writing HTML Viewer failed ({})'.format(str(e)))
Пример #22
0
def generate_html(output_dir='.', doujinshi_obj=None):
    image_html = ''

    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(output_dir, doujinshi_obj.filename)
    else:
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    for image in file_list:
        if not os.path.splitext(image)[1] in ('.jpg', '.png'):
            continue

        image_html += '<img src="{0}" class="image-item"/>\n'\
            .format(image)

    html = readfile('viewer/index.html')
    css = readfile('viewer/styles.css')
    js = readfile('viewer/scripts.js')

    if doujinshi_obj is not None:
        title = doujinshi_obj.name
        if sys.version_info < (3, 0):
            title = title.encode('utf-8')
    else:
        title = 'nHentai HTML Viewer'

    data = html.format(TITLE=title, IMAGES=image_html, SCRIPTS=js, STYLES=css)
    try:
        if sys.version_info < (3, 0):
            with open(os.path.join(doujinshi_dir, 'index.html'), 'w') as f:
                f.write(data)
        else:
            with open(os.path.join(doujinshi_dir, 'index.html'), 'wb') as f:
                f.write(data.encode('utf-8'))

        logger.log(15, 'HTML Viewer has been write to \'{0}\''.format(os.path.join(doujinshi_dir, 'index.html')))
    except Exception as e:
        logger.warning('Writen HTML Viewer failed ({})'.format(str(e)))
Пример #23
0
def generate_cbz(output_dir='.', doujinshi_obj=None, rm_origin_dir=False):
    if doujinshi_obj is not None:
        doujinshi_dir = os.path.join(output_dir, doujinshi_obj.filename)
        cbz_filename = os.path.join(os.path.join(doujinshi_dir, '..'), '%s.cbz' % doujinshi_obj.id)
    else:
        cbz_filename = './doujinshi.cbz'
        doujinshi_dir = '.'

    file_list = os.listdir(doujinshi_dir)
    file_list.sort()

    logger.info('Writing CBZ file to path: {}'.format(cbz_filename))
    with zipfile.ZipFile(cbz_filename, 'w') as cbz_pf:
        for image in file_list:
            image_path = os.path.join(doujinshi_dir, image)
            cbz_pf.write(image_path, image)

    if rm_origin_dir:
        shutil.rmtree(doujinshi_dir, ignore_errors=True)

    logger.log(15, 'Comic Book CBZ file has been write to \'{0}\''.format(doujinshi_dir))
Пример #24
0
def main():
    banner()
    logger.info('Using mirror: {0}'.format(BASE_URL))
    options = cmd_parser()

    doujinshi_ids = []
    doujinshi_list = []

    if options.keyword:
        doujinshis = search_parser(options.keyword, options.page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)
    else:
        doujinshi_ids = options.id

    if doujinshi_ids:
        for id in doujinshi_ids:
            doujinshi_info = doujinshi_parser(id)
            doujinshi_list.append(Doujinshi(**doujinshi_info))
    else:
        exit(0)

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                thread=options.threads, timeout=options.timeout)

        for doujinshi in doujinshi_list:
            doujinshi.downloader = downloader
            doujinshi.download()
            generate_html(options.output_dir, doujinshi)

        if not platform.system() == 'Windows':
            logger.log(15, '🍺 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]
Пример #25
0
def main():
    banner()
    logger.info('Using mirror: {0}'.format(BASE_URL))
    options = cmd_parser()

    doujinshi_ids = []
    doujinshi_list = []

    if options.keyword:
        doujinshis = search_parser(options.keyword, options.page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)
    else:
        doujinshi_ids = options.id

    if doujinshi_ids:
        for id in doujinshi_ids:
            doujinshi_info = doujinshi_parser(id)
            doujinshi_list.append(Doujinshi(**doujinshi_info))
    else:
        exit(0)

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                thread=options.threads, timeout=options.timeout)

        for doujinshi in doujinshi_list:
            doujinshi.downloader = downloader
            doujinshi.download()

        if not platform.system() == 'Windows':
            logger.log(15, '🍺 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]
Пример #26
0
def doujinshi_parser(id_):
    if not isinstance(id_,
                      (int, )) and (isinstance(id_,
                                               (str, )) and not id_.isdigit()):
        raise Exception('Doujinshi id({0}) is not valid'.format(id_))

    id_ = int(id_)
    logger.log(15, 'Fetching doujinshi information of id {0}'.format(id_))
    doujinshi = dict()
    doujinshi['id'] = id_
    url = '{0}/{1}/'.format(constant.DETAIL_URL, id_)

    try:
        response = request('get', url)
        if response.status_code in (200, ):
            response = response.content
        elif response.status_code in (404, ):
            logger.error("Doujinshi with id {0} cannot be found".format(id_))
            return []
        else:
            logger.debug('Slow down and retry ({}) ...'.format(id_))
            time.sleep(1)
            return doujinshi_parser(str(id_))

    except Exception as e:
        logger.warning('Error: {}, ignored'.format(str(e)))
        return None

    html = BeautifulSoup(response, 'html.parser')
    doujinshi_info = html.find('div', attrs={'id': 'info'})

    title = doujinshi_info.find('h1').text
    pretty_name = doujinshi_info.find('h1').find('span',
                                                 attrs={
                                                     'class': 'pretty'
                                                 }).text
    subtitle = doujinshi_info.find('h2')

    doujinshi['name'] = title
    doujinshi['pretty_name'] = pretty_name
    doujinshi['subtitle'] = subtitle.text if subtitle else ''

    doujinshi_cover = html.find('div', attrs={'id': 'cover'})
    img_id = re.search('/galleries/([0-9]+)/cover.(jpg|png|gif)$',
                       doujinshi_cover.a.img.attrs['data-src'])

    ext = []
    for i in html.find_all('div', attrs={'class': 'thumb-container'}):
        _, ext_name = os.path.basename(i.img.attrs['data-src']).rsplit('.', 1)
        ext.append(ext_name)

    if not img_id:
        logger.critical('Tried yo get image id failed')
        exit(1)

    doujinshi['img_id'] = img_id.group(1)
    doujinshi['ext'] = ext

    for _ in doujinshi_info.find_all('div', class_='tag-container field-name'):
        if re.search('Pages:', _.text):
            pages = _.find('span', class_='name').string
    doujinshi['pages'] = int(pages)

    # gain information of the doujinshi
    information_fields = doujinshi_info.find_all('div',
                                                 attrs={'class': 'field-name'})
    needed_fields = [
        'Characters', 'Artists', 'Languages', 'Tags', 'Parodies', 'Groups',
        'Categories'
    ]
    for field in information_fields:
        field_name = field.contents[0].strip().strip(':')
        if field_name in needed_fields:
            data = [
                sub_field.find('span', attrs={
                    'class': 'name'
                }).contents[0].strip()
                for sub_field in field.find_all('a', attrs={'class': 'tag'})
            ]
            doujinshi[field_name.lower()] = ', '.join(data)

    time_field = doujinshi_info.find('time')
    if time_field.has_attr('datetime'):
        doujinshi['date'] = time_field['datetime']
    return doujinshi
Пример #27
0
def main():
    banner()
    logger.info('Using mirror: {0}'.format(BASE_URL))
    options = cmd_parser()

    doujinshi_ids = []
    doujinshi_list = []

    if options.keyword:
        doujinshis = search_parser(options.keyword, options.page)
        print_doujinshi(doujinshis)
        if options.is_download:
            doujinshi_ids = map(lambda d: d['id'], doujinshis)
    else:
        doujinshi_ids = options.id

    if doujinshi_ids:
        for id in doujinshi_ids:
            doujinshi_info = doujinshi_parser(id)
            doujinshi_list.append(Doujinshi(**doujinshi_info))
    else:
        exit(0)

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                thread=options.threads, timeout=options.timeout)

        for doujinshi in doujinshi_list:
            doujinshi.downloader = downloader
            doujinshi.download()

            image_html = ''
            previous = ''

            doujinshi_dir = os.path.join(options.output_dir, str(doujinshi.id))
            file_list = os.listdir(doujinshi_dir)
            file_list.sort()

            for index, image in enumerate(file_list):
                try:
                    next_ = file_list[file_list.index(image) + 1]
                except IndexError:
                    next_ = ''

                image_html += '<img src="{0}" class="image-item {1}" attr-prev="{2}" attr-next="{3}">\n'\
                    .format(image, 'current' if index == 0 else '', previous, next_)
                previous = image

            with open(os.path.join(os.path.dirname(__file__), 'doujinshi.html'), 'r') as template:
                html = template.read()

            data = html.format(TITLE=doujinshi.name, IMAGES=image_html)
            with open(os.path.join(doujinshi_dir, 'index.html'), 'w') as f:
                f.write(data)

            logger.log(15, 'HTML Viewer has been write to \'{0}\''.format(os.path.join(doujinshi_dir, 'index.html')))

        if not platform.system() == 'Windows':
            logger.log(15, '🍺 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]
Пример #28
0
 def _download_callback(self, request, result):
     if not result:
         logger.critical('Too many errors occurred, quit.')
         exit(1)
     logger.log(15, '{0} download successfully'.format(result))
Пример #29
0
def main():
    banner()
    options = cmd_parser()
    logger.info('Using mirror: {0}'.format(BASE_URL))

    from nhentai.constant import PROXY
    # constant.PROXY will be changed after cmd_parser()
    if PROXY != {}:
        logger.info('Using proxy: {0}'.format(PROXY))

    # check your cookie
    check_cookie()

    index = 0
    index_value = None
    doujinshis = []
    doujinshi_ids = []
    doujinshi_list = []

    if options.favorites:
        if not options.is_download:
            logger.warning('You do not specify --download option')

        doujinshis = favorites_parser(options.page_range)

    elif options.tag:
        doujinshis = tag_parser(options.tag,
                                sorting=options.sorting,
                                max_page=options.max_page)

    elif options.artist:
        index = 1
        index_value = options.artist

    elif options.character:
        index = 2
        index_value = options.character

    elif options.parody:
        index = 3
        index_value = options.parody

    elif options.group:
        index = 4
        index_value = options.group

    elif options.language:
        index = 5
        index_value = options.language

    elif options.keyword:
        doujinshis = search_parser(options.keyword,
                                   sorting=options.sorting,
                                   page=options.page)

    elif not doujinshi_ids:
        doujinshi_ids = options.id

    if index:
        doujinshis = tag_parser(index_value,
                                max_page=options.max_page,
                                index=index)

    print_doujinshi(doujinshis)
    if options.is_download and doujinshis:
        doujinshi_ids = [i['id'] for i in doujinshis]

        if options.is_save_download_history:
            with DB() as db:
                data = set(db.get_all())

            doujinshi_ids = list(set(doujinshi_ids) - data)

    if doujinshi_ids:
        for i, id_ in enumerate(doujinshi_ids):
            if options.delay:
                time.sleep(options.delay)

            doujinshi_info = doujinshi_parser(id_)

            if doujinshi_info:
                doujinshi_list.append(
                    Doujinshi(name_format=options.name_format,
                              **doujinshi_info))

            if (i + 1) % 10 == 0:
                logger.info('Progress: %d / %d' % (i + 1, len(doujinshi_ids)))

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                size=options.threads,
                                timeout=options.timeout,
                                delay=options.delay)

        for doujinshi in doujinshi_list:

            doujinshi.downloader = downloader
            doujinshi.download()
            if options.is_save_download_history:
                with DB() as db:
                    db.add_one(doujinshi.id)

            if not options.is_nohtml and not options.is_cbz:
                generate_html(options.output_dir, doujinshi)
            elif options.is_cbz:
                generate_cbz(options.output_dir, doujinshi,
                             options.rm_origin_dir, options.write_comic_info)

        if options.main_viewer:
            generate_main_html(options.output_dir)

        if not platform.system() == 'Windows':
            logger.log(15, '🍻 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]
Пример #30
0
def main():
    banner()

    if sys.version_info < (3, 0, 0):
        logger.error('nhentai now only support Python 3.x')
        exit(1)

    options = cmd_parser()
    logger.info('Using mirror: {0}'.format(BASE_URL))

    # CONFIG['proxy'] will be changed after cmd_parser()
    if constant.CONFIG['proxy']['http']:
        logger.info('Using proxy: {0}'.format(
            constant.CONFIG['proxy']['http']))

    if not constant.CONFIG['template']:
        constant.CONFIG['template'] = 'default'

    logger.info('Using viewer template "{}"'.format(
        constant.CONFIG['template']))

    # check your cookie
    check_cookie()

    doujinshis = []
    doujinshi_ids = []
    doujinshi_list = []

    page_list = paging(options.page)

    if options.favorites:
        if not options.is_download:
            logger.warning('You do not specify --download option')

        doujinshis = favorites_parser(page=page_list)

    elif options.keyword:
        if constant.CONFIG['language']:
            logger.info('Using default language: {0}'.format(
                constant.CONFIG['language']))
            options.keyword += ' language:{}'.format(
                constant.CONFIG['language'])
        doujinshis = search_parser(options.keyword,
                                   sorting=options.sorting,
                                   page=page_list,
                                   is_page_all=options.page_all)

    elif not doujinshi_ids:
        doujinshi_ids = options.id

    print_doujinshi(doujinshis)
    if options.is_download and doujinshis:
        doujinshi_ids = [i['id'] for i in doujinshis]

    if options.is_save_download_history:
        with DB() as db:
            data = map(int, db.get_all())

        doujinshi_ids = list(set(map(int, doujinshi_ids)) - set(data))

    if doujinshi_ids:
        for i, id_ in enumerate(doujinshi_ids):
            if options.delay:
                time.sleep(options.delay)

            doujinshi_info = doujinshi_parser(id_)

            if doujinshi_info:
                doujinshi_list.append(
                    Doujinshi(name_format=options.name_format,
                              **doujinshi_info))

            if (i + 1) % 10 == 0:
                logger.info('Progress: %d / %d' % (i + 1, len(doujinshi_ids)))

    if not options.is_show:
        downloader = Downloader(path=options.output_dir,
                                size=options.threads,
                                timeout=options.timeout,
                                delay=options.delay)

        for doujinshi in doujinshi_list:
            if not options.dryrun:
                doujinshi.downloader = downloader
                doujinshi.download()

            doujinshi.downloader = downloader
            doujinshi.download()

            if options.generate_metadata:
                table = doujinshi.table
                generate_metadata_file(options.output_dir, table, doujinshi)

            if options.is_save_download_history:
                with DB() as db:
                    db.add_one(doujinshi.id)

            if not options.is_nohtml and not options.is_cbz and not options.is_pdf:
                generate_html(options.output_dir,
                              doujinshi,
                              template=constant.CONFIG['template'])
            elif options.is_cbz:
                generate_cbz(options.output_dir, doujinshi,
                             options.rm_origin_dir)
            elif options.is_pdf:
                generate_pdf(options.output_dir, doujinshi,
                             options.rm_origin_dir)

        if options.main_viewer:
            generate_main_html(options.output_dir)

        if not platform.system() == 'Windows':
            logger.log(15, '🍻 All done.')
        else:
            logger.log(15, 'All done.')

    else:
        [doujinshi.show() for doujinshi in doujinshi_list]