def test_download(self): pcs = PCS(self.username, self.password) print 'Quota :' pprint(literal_eval( pcs.quota().content)) headers = {'Range': 'bytes=0-99'} r = pcs.download('/test.txt', headers=headers) print '/test.txt content:' print r.content
class BaiduPan(Cmd): prompt = colored('dupan', 'yellow', attrs = ['bold']) + colored(' >> ', 'red', attrs = ['bold']) completekey = 'tab' editor = 'vim' timing = False debug = True download_root = os.path.join(CWD, 'download') cwd = '/' dirs = {} pcs = None def __init__(self): Cmd.__init__(self) try: import readline readline.set_completer_delims(' \t\n"') # initially it was ' \t\n`!@#$^&*()=+[{]}\\|;:\'",<>?', but I dont want to break on too many except: pass @options([make_option('-u', '--username', help="specify username"), make_option('-p', '--password',help="specify password"), ]) def do_login(self, args, opts): print 'logging in, please wait ...' self.pcs = PCS(opts.username, opts.password, captcha_callback = handle_captcha) self.pcs.get_fastest_pcs_server() res = json.loads(self.pcs.quota().content) if res['errno'] != 0: self.pcs = None print 'login failed: %r' % res return print 'Login success. storage used: %s/%s' % (readable_size(res['used']), readable_size(res['total'])) def do_cd(self, args): if type(args) == type([]): args = args[0] if not isinstance(args, basestring) or not args: print 'cd /path/to/dir' return if args.startswith('/'): self.cwd = args else: self.cwd = os.path.join(self.cwd, args) self.cwd = os.path.normpath(self.cwd) def do_timing(self, args): if not args: print 'timing on|off' return if args.lower() == 'on': self.timing = True elif args.lower() == 'off': self.timing = False else: print 'timing on|off' return def do_pwd(self, args): print self.cwd def do_saveto(self, args): path = args if not path: print 'current download root: %s' % self.download_root return if not path.startswith('/'): path = os.path.normpath(os.path.join(os.getcwd(), path)) self.download_root = path print 'will save to %s' % path def do_ls(self, args): if not self.pcs: print 'please login first' return if not args: path = self.cwd else: path = args path = os.path.normpath(os.path.join(self.cwd, path)) print path res = json.loads(self.pcs.list_files(path).content) # print json.dumps(res, indent = 4) ''' { "isdir": 1, "category": 6, "server_filename": "cs", "local_mtime": 1395372049, "server_ctime": 1395372049, "server_mtime": 1395372049, "fs_id": 640464281820244, "path": "/cs", "size": 0, "local_ctime": 1395372049 } ''' if res.get('errno', None) != 0: log('invalid response: %r' % res, 'yellow') return print 'total %d' % len(res.get('list', [])) content = [] cnt = 0 lst = res.get('list', []) idxsz = len(str(len(lst)-1)) sizes = [] sizesz = 0 for fsitem in lst: t = readable_size(fsitem.get('size')) if len(t) > sizesz: sizesz = len(t) sizes.append(t) for i, fsitem in enumerate(lst): print '[ %s ] %s %s %s %s' % (str(cnt).rjust(idxsz), fsitem.get('isdir', 0) and 'd' or '-', sizes[i].ljust(sizesz, ' '), datetime.datetime.fromtimestamp(fsitem.get('server_mtime', 0)).strftime('%Y-%m-%d_%H:%M:%S'), colored(fsitem.get('server_filename'), fsitem.get('isdir', 0) and 'cyan' or 'white', attrs = ['bold']) + (fsitem.get('isdir', 0) and '/' or '')) cnt += 1 content.append(fsitem.get('server_filename')) self.dirs[path] = lst @options([make_option('-i', '--index', help="the file index to delete, separate with comma, e.g. 3,5,2, also range supported, e.g. 1-4,5,7"), ]) def do_meta(self, args, opts): if not self.pcs: print 'please login first' return args = split_command_line(args) fps = [] if opts.index: if not self.dirs.get(self.cwd): print 'please use `ls` to list dir first to let me know which files you want to operate' return try: indexes = parse_index_param(opts.index, len(self.dirs.get(self.cwd))) fps = [self.dirs.get(self.cwd)[i]['server_filename'] for i in indexes] except Exception, ex: print ex return final = fps + args for path in final: path = os.path.normpath(os.path.join(self.cwd, path)) print path o = json.loads(self.pcs.meta([path]).content) if o.get('errno', None) != 0: print ('invalid request: %r' % o) return size = o['info'][0]['size'] info = o['info'][0] for k in info: print colored(k + ': ', 'cyan'), colored(info[k], 'white')
class BaiduPan(Cmd): prompt = colored('dupan', 'yellow', attrs = ['bold']) + colored(' >> ', 'red', attrs = ['bold']) completekey = 'tab' editor = 'vim' timing = False debug = True download_root = ROOT cwd = '/' dirs = {} pcs = None def __init__(self): Cmd.__init__(self) try: import readline readline.set_completer_delims(' \t\n"') # initially it was ' \t\n`!@#$^&*()=+[{]}\\|;:\'",<>?', but I dont want to break on too many except: pass @options([make_option('-u', '--username', help="specify username"), make_option('-p', '--password',help="specify password"), ]) def do_login(self, args, opts): print 'logging in, please wait ...' self.pcs = PCS(opts.username, opts.password, captcha_callback = handle_captcha) # self.pcs.get_fastest_pcs_server() res = {} for retry in range(3): res = json.loads(self.pcs.quota().content) if res['errno'] == 0: break else: res = {} time.sleep(retry+1) if res.get('errno') == 0: print 'Login success. storage used: %s/%s' % (readable_size(res['used']), readable_size(res['total'])) else: print 'login failed: %r' % res def do_cd(self, args): if type(args) == type([]): args = args[0] if not isinstance(args, basestring) or not args: print 'cd /path/to/dir' return if args.startswith('/'): self.cwd = args else: self.cwd = os.path.join(self.cwd, args) self.cwd = os.path.normpath(self.cwd) def do_timing(self, args): if not args: print 'timing on|off' return if args.lower() == 'on': self.timing = True elif args.lower() == 'off': self.timing = False else: print 'timing on|off' return def do_pwd(self, args): print self.cwd def do_saveto(self, args): path = args if not path: print 'current download root: %s' % self.download_root return if not path.startswith('/'): path = os.path.normpath(os.path.join(os.getcwd(), path)) self.download_root = path print 'will save to %s' % path def do_ls(self, args): if not self.pcs: print 'please login first' return if not args: path = self.cwd else: path = args path = os.path.normpath(os.path.join(self.cwd, path)) print path res = json.loads(self.pcs.list_files(path).content) # print json.dumps(res, indent = 4) ''' { "isdir": 1, "category": 6, "server_filename": "cs", "local_mtime": 1395372049, "server_ctime": 1395372049, "server_mtime": 1395372049, "fs_id": 640464281820244, "path": "/cs", "size": 0, "local_ctime": 1395372049 } ''' if res.get('errno', None) != 0: log('invalid response: %r' % res, 'yellow') return print 'total %d' % len(res.get('list', [])) content = [] cnt = 0 lst = res.get('list', []) idxsz = len(str(len(lst)-1)) sizes = [] sizesz = 0 for fsitem in lst: t = readable_size(fsitem.get('size')) if len(t) > sizesz: sizesz = len(t) sizes.append(t) for i, fsitem in enumerate(lst): print '[ %s ] %s %s %s %s' % (str(cnt).rjust(idxsz), fsitem.get('isdir', 0) and 'd' or '-', sizes[i].ljust(sizesz, ' '), datetime.datetime.fromtimestamp(fsitem.get('server_mtime', 0)).strftime('%Y-%m-%d_%H:%M:%S'), colored(fsitem.get('server_filename'), fsitem.get('isdir', 0) and 'cyan' or 'white', attrs = ['bold']) + (fsitem.get('isdir', 0) and '/' or '')) cnt += 1 content.append(fsitem.get('server_filename')) self.dirs[path] = lst @options([make_option('-i', '--index', help="the file index to delete, separate with comma, e.g. 3,5,2, also range supported, e.g. 1-4,5,7"), ]) def do_meta(self, args, opts): if not self.pcs: print 'please login first' return args = split_command_line(args) fps = [] if opts.index: if not self.dirs.get(self.cwd): print 'please use `ls` to list dir first to let me know which files you want to operate' return try: indexes = parse_index_param(opts.index, len(self.dirs.get(self.cwd))) fps = [self.dirs.get(self.cwd)[i]['server_filename'] for i in indexes] except Exception, ex: print ex return final = fps + args for path in final: path = os.path.normpath(os.path.join(self.cwd, path)) print path o = json.loads(self.pcs.meta([path]).content) if o.get('errno', None) != 0: print ('invalid request: %r' % o) return size = o['info'][0]['size'] info = o['info'][0] for k in info: print colored(k + ': ', 'cyan'), colored(info[k], 'white')
class BaiduPCS(object): """ Baidu disk uploader. """ def __init__(self, filepath, username, password): """ Login """ (self.filepath, self.filename, self.dirname, self.filesize) = (filepath, os.path.basename(filepath), os.path.dirname(filepath), os.path.getsize(filepath)) self.path = self.dirname + '\\' + self.filename.split('.')[0] self.pcs = PCS(username, password) #Login def create_upload(self, num): self.uplog['md5'][num] = (json.loads( self.pcs.upload_tmpfile(self.block( (num - 1) * self.chinksize)).content)['md5']) self.count += 1 with open(self.dirname + '\\' + self.filename.split('.')[0] + '.json', 'w') as self.new_uplog: json.dump(self.uplog, self.new_uplog) print('[' + str(self.count) + '/' + str(self.fid) + ' Uploaded BlockID: ' + str(num) + ' md5: ' + self.uplog['md5'][num] + ']') def read_uplog(self): if os.path.exists(self.dirname + '\\' + self.filename.split('.')[0] + '.json'): with open( self.dirname + '\\' + self.filename.split('.')[0] + '.json', 'r') as self.uplog_file: self.uplog = json.load(self.uplog_file) tmp_dict = {} for i in sorted(self.uplog['md5'].keys()): tmp_dict[int(i)] = self.uplog['md5'][i] self.uplog['md5'] = tmp_dict else: self.uplog_file = open( self.dirname + '\\' + self.filename.split('.')[0] + '.json', 'w') self.uplog = {'block': 0, 'size': 0, 'md5': {}} def block(self, location=None): if location == None: return math.ceil(os.path.getsize(self.filepath) / self.chinksize) file = open(self.filepath, 'rb') file.seek(location, 0) return io.BytesIO(file.read(self.chinksize)) def upload(self): """ Biadu upload module """ self.read_uplog() if int(self.uplog['size']) == 0: self.chinksize = 1024 * 1024 * 24 self.uplog['size'] = self.chinksize else: self.chinksize = self.uplog['size'] self.thread_num = 25 if int(self.uplog['block']) == 0: self.fid = self.block() self.count = len(self.uplog['md5']) with open(self.dirname + '\\' + self.filename.split('.')[0] + '.json', 'w') as self.new_uplog: json.dump(self.uplog, self.new_uplog) print('start uploading...') self.threads = [] for i in range(self.fid): if not i + 1 in self.uplog['md5']: while len(threading.enumerate()) - 1 >= self.thread_num: time.sleep(1) self.t = threading.Thread(target=self.create_upload, kwargs={'num': i + 1}) self.t.setDaemon(True) self.t.start() self.threads.append(self.t) for self.thread in self.threads: self.thread.join() def superfile(self): self.pcs.upload_superfile('/' + self.filename, [(self.uplog['md5'][k]) for k in sorted(self.uplog['md5'].keys())]) def CheckUpload(self): """ Check upload status. Retry if file not uploaded. """ if not self.fid == len(self.uplog['md5']): return 0 return 1 def quota_remaining(self): self.quota_info = json.loads(self.pcs.quota().content.decode( "utf-8", "ignore")) self.remaining = self.quota_info['total'] - self.quota_info['used'] return self.remaining
from baidupcsapi import PCS pcs = PCS('17624071108', '') print(pcs.quota().content) print(pcs.list_files('/').content)
from baidupcsapi import PCS pcs = PCS('lpbirdueng', 'lupeng') #pcs.info(verify=False) print pcs.quota().content print pcs.list_files('/').content