disktag = $tag; $this->redirect_uri = 'https://scfonedrive.github.io'; if (getConfig('client_id', $tag) && getConfig('client_secret', $tag)) { $this->client_id = getConfig('client_id', $tag); $this->client_secret = getConfig('client_secret', $tag); } else { $this->client_id = '734ef928-d74c-4555-8d1b-d942fa0a1a41'; $this->client_secret = '_I5gOpmG5vTC2Ts_K._wCW4nN1km~4Pk52'; } $this->oauth_url = 'https://login.microsoftonline.com/common/oauth2/v2.0/'; $this->api_url = 'https://graph.microsoft.com/v1.0'; $this->scope = 'https://graph.microsoft.com/Files.ReadWrite.All offline_access'; $this->client_secret = urlencode($this->client_secret); $this->scope = urlencode($this->scope); $this->DownurlStrName = '@microsoft.graph.downloadUrl'; $this->ext_api_url = '/me/drive/root'; $res = $this->get_access_token(getConfig('refresh_token', $tag)); } public function isfine() { if (!$this->access_token) return false; else return true; } public function show_base_class() { return get_class(); //$tmp[0] = get_class(); //$tmp[1] = get_class($this); //return $tmp; } public function ext_show_innerenv() { return []; } public function list_files($path = '/') { global $exts; if (!($files = getcache('path_' . $path, $this->disktag))) { // https://docs.microsoft.com/en-us/graph/api/driveitem-get?view=graph-rest-1.0 // https://docs.microsoft.com/zh-cn/graph/api/driveitem-put-content?view=graph-rest-1.0&tabs=http // https://developer.microsoft.com/zh-cn/graph/graph-explorer $pos = splitlast($path, '/'); $parentpath = $pos[0]; if ($parentpath=='') $parentpath = '/'; $filename = $pos[1]; if ($parentfiles = getcache('path_' . $parentpath, $this->disktag)) { if (isset($parentfiles['children'][$filename][$this->DownurlStrName])) { if (in_array(splitlast($filename,'.')[1], $exts['txt'])) { if (!(isset($parentfiles['children'][$filename]['content'])&&$parentfiles['children'][$filename]['content']['stat']==200)) { $content1 = curl('GET', $parentfiles['children'][$filename][$this->DownurlStrName]); $parentfiles['children'][$filename]['content'] = $content1; savecache('path_' . $parentpath, $parentfiles, $this->disktag); } } return $this->files_format($parentfiles['children'][$filename]); } } $url = $this->api_url . $this->ext_api_url; if ($path !== '/') { $url .= ':' . $path; if (substr($url,-1)=='/') $url=substr($url,0,-1); } $url .= '?expand=children(select=id,name,size,file,folder,parentReference,lastModifiedDateTime,'.$this->DownurlStrName.')'; $arr = $this->MSAPI('GET', $url); //echo $url . '
' . json_encode($arr, JSON_PRETTY_PRINT) . '
'; if ($arr['stat']<500) { $files = json_decode($arr['body'], true); //echo '
' . json_encode($files, JSON_PRETTY_PRINT) . '
'; if (isset($files['folder'])) { if ($files['folder']['childCount']>200) { // files num > 200 , then get nextlink $page = $_POST['pagenum']==''?1:$_POST['pagenum']; if ($page>1) //if (!($files = getcache('path_1' . $path . '_' . $page, $this->disktag))) { $children = $this->fetch_files_children($path, $page); //echo '
' . json_encode($children, JSON_PRETTY_PRINT) . '
'; $files['children'] = $children['value']; //$files['children'] = children_name($files['children']); $files['folder']['page'] = $page; //savecache('path_' . $path . '_' . $page, $files, $this->disktag); } } else { // files num < 200 , then cache //if (isset($files['children'])) { //$files['children'] = children_name($files['children']); //} savecache('path_' . $path, $files, $this->disktag); } } if (isset($files['file'])) { if (in_array(splitlast($files['name'],'.')[1], $exts['txt'])) { if (!(isset($files['content'])&&$files['content']['stat']==200)) { $content1 = curl('GET', $files[$this->DownurlStrName]); $files['content'] = $content1; savecache('path_' . $path, $files, $this->disktag); } } } if (isset($files['error'])) { $files['error']['stat'] = $arr['stat']; } } else { //error_log1($arr['body']); $files = json_decode($arr['body'], true); if (isset($files['error'])) { $files['error']['stat'] = $arr['stat']; } else { $files['error']['stat'] = 503; $files['error']['code'] = 'unknownError'; $files['error']['message'] = 'unknownError'; } //$files = json_decode( '{"unknownError":{ "stat":'.$arr['stat'].',"message":"'.$arr['body'].'"}}', true); //error_log1(json_encode($files, JSON_PRETTY_PRINT)); } } //echo '
' . json_encode($files, JSON_PRETTY_PRINT) . '
'; return $this->files_format($files); } protected function files_format($files) { if (isset($files['file'])) { $tmp['type'] = 'file'; $tmp['id'] = $files['id']; $tmp['name'] = $files['name']; $tmp['time'] = $files['lastModifiedDateTime']; $tmp['size'] = $files['size']; $tmp['mime'] = $files['file']['mimeType']; $tmp['url'] = $files[$this->DownurlStrName]; $tmp['content'] = $files['content']; } elseif (isset($files['folder'])) { $tmp['type'] = 'folder'; $tmp['id'] = $files['id']; $tmp['name'] = $files['name']; $tmp['time'] = $files['lastModifiedDateTime']; $tmp['size'] = $files['size']; $tmp['childcount'] = $files['folder']['childCount']; $tmp['page'] = $files['folder']['page']; foreach ($files['children'] as $file) { $filename = strtolower($file['name']); if (isset($file['file'])) { $tmp['list'][$filename]['type'] = 'file'; //var_dump($file); //echo $file['name'] . ':' . $this->DownurlStrName . ':' . $file[$this->DownurlStrName] . PHP_EOL; $tmp['list'][$filename]['url'] = $file[$this->DownurlStrName]; $tmp['list'][$filename]['mime'] = $file['file']['mimeType']; } elseif (isset($file['folder'])) { $tmp['list'][$filename]['type'] = 'folder'; } $tmp['list'][$filename]['id'] = $file['id']; $tmp['list'][$filename]['name'] = $file['name']; $tmp['list'][$filename]['time'] = $file['lastModifiedDateTime']; $tmp['list'][$filename]['size'] = $file['size']; } } elseif (isset($files['error'])) { return $files; } //error_log1(json_encode($tmp)); return $tmp; } protected function fetch_files_children($path, $page, $getNextlink = false) { $children = getcache('files_' . $path . '_page_' . $page, $this->disktag); if (!$children) { $url = $this->api_url . $this->ext_api_url; if ($path !== '/') { $url .= ':' . $path; if (substr($url,-1)=='/') $url=substr($url,0,-1); $url .= ':'; } $url .= '/children?$top=' . ($page-1)*200 . '&$select=id,name,size,file,folder,parentReference,lastModifiedDateTime,' . $this->DownurlStrName; $children_tmp = json_decode($this->MSAPI('GET', $url)['body'], true); //echo $url . '
' . json_encode($children_tmp, JSON_PRETTY_PRINT) . '
'; $p = 1; $i = 0; foreach ($children_tmp['value'] as $child) { $i++; $value_name = 'child_' . $p; ${$value_name}['value'][] = $child; if ($i==200) { savecache('files_' . $path . '_page_' . $p, ${$value_name}, $this->disktag); unset(${$value_name}); $i = 0; $p++; } } $url = $children_tmp['@odata.nextLink']; $children_tmp = json_decode($this->MSAPI('GET', $url)['body'], true); //echo $url . '
' . json_encode($children_tmp, JSON_PRETTY_PRINT) . '
'; $p = $page; $i = 0; foreach ($children_tmp['value'] as $child) { $i++; $value_name = 'child_' . $p; ${$value_name}['value'][] = $child; if ($i==200) { savecache('files_' . $path . '_page_' . $p, ${$value_name}, $this->disktag); //unset(${$value_name}); $i = 0; $p++; } } if ($i!=0) savecache('files_' . $path . '_page_' . $p, ${$value_name}, $this->disktag); $value_name = 'child_' . $page; return ${$value_name}; } return $children; /*if ($getNextlink) { if (isset($children['@odata.nextLink'])) { return $children; } else { if ($page*200>9800) { $children_tmp = fetch_files_children($path, floor($page/49)*49, 1); $url = $children_tmp['@odata.nextLink']; $children = json_decode(curl('GET', $url, false, ['Authorization' => 'Bearer ' . $this->access_token])['body'], true); } } }*/ } protected function fetch_files_children1($files, $path, $page) { $maxpage = ceil($files['folder']['childCount']/200); if (!($children = getcache('files_' . $path . '_page_' . $page, $this->disktag))) { $pageinfochange=0; for ($page1=$page;$page1>=1;$page1--) { $page3=$page1-1; $url = getcache('nextlink_' . $path . '_page_' . $page3, $this->disktag); if ($url == '') { if ($page1==1) { $url = $this->api_url . $this->ext_api_url; if ($path !== '/') { $url .= ':' . $path; if (substr($url,-1)=='/') $url=substr($url,0,-1); $url .= ':'; } $url .= '/children?$select=id,name,size,file,folder,parentReference,lastModifiedDateTime,'.$this->DownurlStrName; $children = json_decode($this->MSAPI('GET', $url)['body'], true); // echo $url . '
' . json_encode($children, JSON_PRETTY_PRINT) . '
'; savecache('files_' . $path . '_page_' . $page1, $children, $this->disktag); $nextlink=getcache('nextlink_' . $path . '_page_' . $page1, $this->disktag); if ($nextlink!=$children['@odata.nextLink']) { savecache('nextlink_' . $path . '_page_' . $page1, $children['@odata.nextLink'], $this->disktag); $pageinfocache['nextlink_' . $path . '_page_' . $page1] = $children['@odata.nextLink']; $pageinfocache = clearbehindvalue($path,$page1,$maxpage,$pageinfocache); $pageinfochange = 1; } $url = $children['@odata.nextLink']; for ($page2=$page1+1;$page2<=$page;$page2++) { sleep(1); $children = json_decode($this->MSAPI('GET', $url)['body'], true); savecache('files_' . $path . '_page_' . $page2, $children, $this->disktag); $nextlink=getcache('nextlink_' . $path . '_page_' . $page2, $this->disktag); if ($nextlink!=$children['@odata.nextLink']) { savecache('nextlink_' . $path . '_page_' . $page2, $children['@odata.nextLink'], $this->disktag); $pageinfocache['nextlink_' . $path . '_page_' . $page2] = $children['@odata.nextLink']; $pageinfocache = clearbehindvalue($path,$page2,$maxpage,$pageinfocache); $pageinfochange = 1; } $url = $children['@odata.nextLink']; } //echo $url . '
' . json_encode($children, JSON_PRETTY_PRINT) . '
'; return $children; /* $files['children'] = $children['value']; $files['folder']['page']=$page; $pageinfocache['filenum'] = $files['folder']['childCount']; $pageinfocache['dirsize'] = $files['size']; $pageinfocache['cachesize'] = $cachefile['size']; $pageinfocache['size'] = $files['size']-$cachefile['size']; if ($pageinfochange == 1) $this->MSAPI('PUT', path_format($path.'/'.$cachefilename), json_encode($pageinfocache, JSON_PRETTY_PRINT))['body']; return $files;*/ } } else { for ($page2=$page3+1;$page2<=$page;$page2++) { sleep(1); $children = json_decode($this->MSAPI('GET', $url)['body'], true); savecache('files_' . $path . '_page_' . $page2, $children, $this->disktag, 3300); $nextlink=getcache('nextlink_' . $path . '_page_' . $page2, $this->disktag); if ($nextlink!=$children['@odata.nextLink']) { savecache('nextlink_' . $path . '_page_' . $page2, $children['@odata.nextLink'], $this->disktag, 3300); $pageinfocache['nextlink_' . $path . '_page_' . $page2] = $children['@odata.nextLink']; $pageinfocache = clearbehindvalue($path,$page2,$maxpage,$pageinfocache); $pageinfochange = 1; } $url = $children['@odata.nextLink']; } //echo $url . '
' . json_encode($children, JSON_PRETTY_PRINT) . '
'; return $children; /*$files['children'] = $children['value']; $files['folder']['page']=$page; $pageinfocache['filenum'] = $files['folder']['childCount']; $pageinfocache['dirsize'] = $files['size']; $pageinfocache['cachesize'] = $cachefile['size']; $pageinfocache['size'] = $files['size']-$cachefile['size']; if ($pageinfochange == 1) $this->MSAPI('PUT', path_format($path.'/'.$cachefilename), json_encode($pageinfocache, JSON_PRETTY_PRINT))['body']; return $files;*/ } } }/* else { $files['folder']['page']=$page; for ($page4=1;$page4<=$maxpage;$page4++) { if (!($url = getcache('nextlink_' . $path . '_page_' . $page4, $this->disktag))) { if ($files['folder'][$path.'_'.$page4]!='') savecache('nextlink_' . $path . '_page_' . $page4, $files['folder'][$path.'_'.$page4], $this->disktag); } else { $files['folder'][$path.'_'.$page4] = $url; } } }*/ return $children; //return $files; } public function Rename($file, $newname) { $oldname = spurlencode($file['name']); $oldname = path_format($file['path'] . '/' . $oldname); $data = '{"name":"' . $newname . '"}'; //echo $oldname; $result = $this->MSAPI('PATCH', $oldname, $data); return output(json_encode($this->files_format(json_decode($result['body'], true))), $result['stat']); } public function Delete($file) { $filename = spurlencode($file['name']); $filename = path_format($file['path'] . '/' . $filename); //echo $filename; $result = $this->MSAPI('DELETE', $filename); return output(json_encode($this->files_format(json_decode($result['body'], true))), $result['stat']); return output($result['body'], $result['stat']); } public function Encrypt($folder, $passfilename, $pass) { $filename = path_format($folder['path'] . '/' . urlencode($passfilename)); if ($pass==='') { $result = $this->MSAPI('DELETE', $filename, ''); } else { $result = $this->MSAPI('PUT', $filename, $pass); } $path1 = $folder['path']; if ($path1!='/'&&substr($path1, -1)=='/') $path1 = substr($path1, 0, -1); savecache('path_' . $path1 . '/?password', '', $this->disktag, 1); return output(json_encode($this->files_format(json_decode($result['body'], true))), $result['stat']); return output($result['body'], $result['stat']); } public function Move($file, $folder) { $filename = spurlencode($file['name']); $filename = path_format($file['path'] . '/' . $filename); $data = '{"parentReference":{"path": "/drive/root:' . $folder['path'] . '"}}'; $result = $this->MSAPI('PATCH', $filename, $data); $path2 = spurlencode($folder['path'], '/'); if ($path2!='/'&&substr($path2, -1)=='/') $path2 = substr($path2, 0, -1); savecache('path_' . $path2, json_decode('{}', true), $this->disktag, 1); return output(json_encode($this->files_format(json_decode($result['body'], true))), $result['stat']); return output($result['body'], $result['stat']); } public function Copy($file) { $filename = spurlencode($file['name']); $filename = path_format($file['path'] . '/' . $filename); $namearr = splitlast($file['name'], '.'); date_default_timezone_set('UTC'); if ($namearr[0]!='') { $newname = $namearr[0] . ' (' . date("Ymd\THis\Z") . ')'; if ($namearr[1]!='') $newname .= '.' . $namearr[1]; } else { $newname = '.' . $namearr[1] . ' (' . date("Ymd\THis\Z") . ')'; } $data = '{ "name": "' . $newname . '" }'; $result = $this->MSAPI('copy', $filename, $data); /*$num = 0; while ($result['stat']==409 && json_decode($result['body'], true)['error']['code']=='nameAlreadyExists') { $num++; if ($namearr[0]!='') { $newname = $namearr[0] . ' (' . getconstStr('Copy') . ' ' . $num . ')'; if ($namearr[1]!='') $newname .= '.' . $namearr[1]; } else { $newname = '.' . $namearr[1] . ' ('.getconstStr('Copy'). ' ' . $num .')'; } //$newname = spurlencode($newname); $data = '{ "name": "' . $newname . '" }'; $result = $this->MSAPI('copy', $filename, $data); }*/ return output(json_encode($this->files_format(json_decode($result['body'], true))), $result['stat']); return output($result['body'], $result['stat']); } public function Edit($file, $content) { /*TXT一般不会超过4M,不用二段上传 $filename = $path1 . ':/createUploadSession'; $response=MSAPI('POST',$filename,'{"item": { "@microsoft.graph.conflictBehavior": "replace" }}',$_SERVER['access_token']); $uploadurl=json_decode($response,true)['uploadUrl']; echo MSAPI('PUT',$uploadurl,$data,$_SERVER['access_token']);*/ $result = $this->MSAPI('PUT', $file['path'], $content); //return output($result['body'], $result['stat']); //echo $result; $resultarry = json_decode($result['body'],true); if (isset($resultarry['error'])) return message($resultarry['error']['message']. '
'.getconstStr('Back').'','Error', 403); else return output('success', 0); } public function Create($parent, $type, $name, $content = '') { if ($type=='file') { $filename = spurlencode($name); $filename = path_format($parent['path'] . '/' . $filename); $result = $this->MSAPI('PUT', $filename, $content); } if ($type=='folder') { $data = '{ "name": "' . $name . '", "folder": { }, "@microsoft.graph.conflictBehavior": "rename" }'; $result = $this->MSAPI('children', $parent['path'], $data); } //savecache('path_' . $path1, json_decode('{}',true), $_SERVER['disktag'], 1); return output(json_encode($this->files_format(json_decode($result['body'], true))), $result['stat']); return output($result['body'], $result['stat']); } public function AddDisk() { global $constStr; global $EnvConfigs; $envs = ''; foreach ($EnvConfigs as $env => $v) if (isCommonEnv($env)) $envs .= '\'' . $env . '\', '; $url = path_format($_SERVER['PHP_SELF'] . '/'); //$this->api_url = splitfirst($_SERVER['api_url'], '/v1.0')[0] . '/v1.0'; if (isset($_GET['Finish'])) { if ($this->access_token == '') { $refresh_token = getConfig('refresh_token', $this->disktag); if (!$refresh_token) { $html = 'No refresh_token config, please AddDisk again or wait minutes.
' . $this->disktag; $title = 'Error'; return message($html, $title, 201); } $response = $this->get_access_token($refresh_token); if (!$response) return message($this->error['body'], $this->error['stat'] . ' Error', $this->error['stat']); } $tmp = null; if ($_POST['DriveType']=='Onedrive') { /*$api = $this->api_url . '/me'; $arr = curl('GET', $api, '', [ 'Authorization' => 'Bearer ' . $this->access_token ], 1); if ($arr['stat']==200) { $userid = json_decode($arr['body'], true)['id']; $api = $this->api_url . '/users/' . $userid . '/drive'; $arr = curl('GET', $api, '', [ 'Authorization' => 'Bearer ' . $this->access_token ], 1); if ($arr['stat']!=200) return message($arr['stat'] . '
' . $api . '
' . $arr['body'], 'Get User Drive ID', $arr['stat']); $tmp['DriveId'] = json_decode($arr['body'], true)['id']; } elseif ($arr['stat']==403||$arr['stat']==401) { // 403:世纪不让列me,401:个人也不给拿 $api = $this->api_url . '/me/drive'; } else { return message($arr['stat'] . $arr['body'], 'Get User ID', $arr['stat']); }*/ if (get_class($this)=='Sharepoint') $tmp['Driver'] = 'Onedrive'; elseif (get_class($this)=='SharepointCN') $tmp['Driver'] = 'OnedriveCN'; $tmp['sharepointSite'] = ''; $tmp['siteid'] = ''; } elseif ($_POST['DriveType']=='Custom') { // sitename计算siteid $tmp1 = $this->get_siteid($_POST['sharepointSite']); if (isset($tmp1['stat'])) return message($arr['stat'] . $tmp1['body'], 'Get Sharepoint Site ID ' . $_POST['sharepointSite'], $tmp1['stat']); $siteid = $tmp1; //$api = $this->api_url . '/sites/' . $siteid . '/drive/'; //$arr = curl('GET', $api, '', [ 'Authorization' => 'Bearer ' . $this->access_token ], 1); //if ($arr['stat']!=200) return message($arr['stat'] . $arr['body'], 'Get Sharepoint Drive ID ' . $_POST['DriveType'], $arr['stat']); $tmp['siteid'] = $siteid; $tmp['sharepointSite'] = $_POST['sharepointSite']; if (get_class($this)=='Onedrive') $tmp['Driver'] = 'Sharepoint'; elseif (get_class($this)=='OnedriveCN') $tmp['Driver'] = 'SharepointCN'; } else { // 直接是siteid $tmp['siteid'] = $_POST['DriveType']; $tmp['sharepointSite'] = $_POST['sharepointSiteUrl']; if (get_class($this)=='Onedrive') $tmp['Driver'] = 'Sharepoint'; elseif (get_class($this)=='OnedriveCN') $tmp['Driver'] = 'SharepointCN'; } $response = setConfigResponse( setConfig($tmp, $this->disktag) ); if (api_error($response)) { $html = api_error_msg($response); $title = 'Error'; return message($html, $title, 201); } else { $str .= ' '; return message($str, getconstStr('WaitJumpIndex'), 201); } } if (isset($_GET['SelectDrive'])) { if (get_class($this)=='Sharelink') return message('Can not change to other.', 'Back', 201); if ($this->access_token == '') { $refresh_token = getConfig('refresh_token', $this->disktag); if (!$refresh_token) { $html = 'No refresh_token config, please AddDisk again or wait minutes.
' . $this->disktag; $title = 'Error'; return message($html, $title, 201); } $response = $this->get_access_token($refresh_token); if (!$response) return message($this->error['body'], $this->error['stat'] . ' Error', $this->error['stat']); } $api = $this->api_url . '/sites/root'; $arr = curl('GET', $api, '', [ 'Authorization' => 'Bearer ' . $this->access_token ]); $Tenant = json_decode($arr['body'], true)['webUrl']; $api = $this->api_url . '/me/followedSites'; $arr = curl('GET', $api, '', [ 'Authorization' => 'Bearer ' . $this->access_token ]); if (!($arr['stat']==200||$arr['stat']==403||$arr['stat']==400||$arr['stat']==404)) return message($arr['stat'] . json_encode(json_decode($arr['body']), JSON_PRETTY_PRINT), 'Get followedSites', $arr['stat']); error_log1($arr['body']); $sites = json_decode($arr['body'], true)['value']; $title = 'Select Driver'; $html = '

'; if ($sites[0]!='') foreach ($sites as $k => $v) { $html .= ' '; } $html .= '
'; $html .= '
'; return message($html, $title, 201); } if (isset($_GET['install2']) && isset($_GET['code'])) { $tmp = curl('POST', $this->oauth_url . 'token', 'client_id=' . $this->client_id .'&client_secret=' . $this->client_secret . '&grant_type=authorization_code&requested_token_use=on_behalf_of&redirect_uri=' . $this->redirect_uri . '&code=' . $_GET['code']); if ($tmp['stat']==200) $ret = json_decode($tmp['body'], true); if (isset($ret['refresh_token'])) { $refresh_token = $ret['refresh_token']; $str = ' refresh_token :
'; $str .= '

' . getconstStr('SavingToken') . ' '; $tmptoken['refresh_token'] = $refresh_token; $tmptoken['token_expires'] = time()+7*24*60*60; $response = setConfigResponse( setConfig($tmptoken, $this->disktag) ); if (api_error($response)) { $html = api_error_msg($response); $title = 'Error'; return message($html, $title, 201); } else { savecache('access_token', $ret['access_token'], $this->disktag, $ret['expires_in'] - 60); $str .= ' '; return message($str, getconstStr('Wait') . ' 3s', 201); } } return message('
' . json_encode(json_decode($tmp['body']), JSON_PRETTY_PRINT) . '
', $tmp['stat']); //return message('
' . json_encode($ret, JSON_PRETTY_PRINT) . '
', 500); } if (isset($_GET['install1'])) { if (get_class($this)=='Onedrive' || get_class($this)=='OnedriveCN') { return message(' ' . getconstStr('JumptoOffice') . ' ', getconstStr('Wait') . ' 1s', 201); } else { return message('Something error, retry after a few seconds.', 'Retry', 201); } } if (isset($_GET['install0'])) { if ($_POST['disktag_add']!='') { $_POST['disktag_add'] = preg_replace('/[^0-9a-zA-Z|_]/i', '', $_POST['disktag_add']); $f = substr($_POST['disktag_add'], 0, 1); if (strlen($_POST['disktag_add'])==1) $_POST['disktag_add'] .= '_'; if (isCommonEnv($_POST['disktag_add'])) { return message('Do not input ' . $envs . '
', 'Error', 201); } elseif (!(('a'<=$f && $f<='z') || ('A'<=$f && $f<='Z'))) { return message('Please start with letters
', 'Error', 201); } $tmp = null; // clear envs foreach ($EnvConfigs as $env => $v) if (isInnerEnv($env)) $tmp[$env] = ''; //$this->disktag = $_POST['disktag_add']; $tmp['disktag_add'] = $_POST['disktag_add']; $tmp['diskname'] = $_POST['diskname']; $tmp['Driver'] = $_POST['Drive_ver']; if ($_POST['Drive_ver']=='Sharelink') { $tmp['shareurl'] = $_POST['shareurl']; } else { if ($_POST['Drive_ver']=='Onedrive' && $_POST['NT_Drive_custom']=='on') { $tmp['client_id'] = $_POST['NT_client_id']; $tmp['client_secret'] = $_POST['NT_client_secret']; } elseif ($_POST['Drive_ver']=='OnedriveCN' && $_POST['CN_Drive_custom']=='on') { $tmp['client_id'] = $_POST['CN_client_id']; $tmp['client_secret'] = $_POST['CN_client_secret']; } } $response = setConfigResponse( setConfig($tmp, $this->disktag) ); if (api_error($response)) { $html = api_error_msg($response); $title = 'Error'; } else { $title = getconstStr('MayinEnv'); $html = getconstStr('Wait') . ' 3s'; if ($_POST['Drive_ver']=='Sharelink') $html = getconstStr('Wait') . ' 3s'; } return message($html, $title, 201); } } $html = '
' . getconstStr('DiskTag') . ': (' . getConfig('disktag') . ')
' . getconstStr('DiskName') . ':







'; if ($_SERVER['language']=='zh-cn') $html .= '你要理解 scfonedrive.github.io 是github上的静态网站,
除非github真的挂掉了,
不然,稍后你如果连不上,请检查你的运营商或其它“你懂的”问题!
'; $html .='
'; $title = 'Select Account Type'; return message($html, $title, 201); } protected function get_access_token($refresh_token) { if (!$refresh_token) { $tmp['stat'] = 0; $tmp['body'] = 'No refresh_token'; $this->error = $tmp; return false; } if (!($this->access_token = getcache('access_token', $this->disktag))) { $p=0; while ($response['stat']==0&&$p<3) { $response = curl('POST', $this->oauth_url . 'token', 'client_id=' . $this->client_id . '&client_secret=' . $this->client_secret . '&grant_type=refresh_token&requested_token_use=on_behalf_of&refresh_token=' . $refresh_token ); $p++; } if ($response['stat']==200) $ret = json_decode($response['body'], true); if (!isset($ret['access_token'])) { error_log1($this->oauth_url . 'token' . '?client_id=' . $this->client_id . '&client_secret=' . $this->client_secret . '&grant_type=refresh_token&requested_token_use=on_behalf_of&refresh_token=' . substr($refresh_token, 0, 20) . '******' . substr($refresh_token, -20)); error_log1('failed to get [' . $this->disktag . '] access_token. response: ' . $response['body']); $response['body'] = json_encode(json_decode($response['body']), JSON_PRETTY_PRINT); $response['body'] .= '\nfailed to get [' . $this->disktag . '] access_token.'; $this->error = $response; return false; //throw new Exception($response['stat'].', failed to get ['.$this->disktag.'] access_token.'.$response['body']); } $tmp = $ret; $tmp['access_token'] = substr($tmp['access_token'], 0, 10) . '******'; $tmp['refresh_token'] = substr($tmp['refresh_token'], 0, 10) . '******'; error_log1('[' . $this->disktag . '] Get access token:' . json_encode($tmp, JSON_PRETTY_PRINT)); $this->access_token = $ret['access_token']; savecache('access_token', $this->access_token, $this->disktag, $ret['expires_in'] - 300); if (time()>getConfig('token_expires', $this->disktag)) setConfig([ 'refresh_token' => $ret['refresh_token'], 'token_expires' => time()+7*24*60*60 ], $this->disktag); return true; } return true; } protected function get_siteid($sharepointSite) { //$sharepointSite = getConfig('sharepointSite', $this->disktag); while (substr($sharepointSite, -1)=='/') $sharepointSite = substr($sharepointSite, 0, -1); $tmp = splitlast($sharepointSite, '/'); if ($tmp[1]==urldecode($tmp[1])) { $sharepointname = urlencode($tmp[1]); } else { $sharepointname = $tmp[1]; } $tmp = splitlast($tmp[0], '/'); if (getConfig('Driver', $this->disktag)=='Onedrive') $url = 'https://graph.microsoft.com/v1.0/sites/root:/' . $tmp[1] . '/' . $sharepointname; if (getConfig('Driver', $this->disktag)=='OnedriveCN') $url = 'https://microsoftgraph.chinacloudapi.cn/v1.0/sites/root:/' . $tmp[1] . '/' . $sharepointname; $i=0; $response = []; while ($url!=''&&$response['stat']!=200&&$i<4) { $response = curl('GET', $url, false, ['Authorization' => 'Bearer ' . $this->access_token]); $i++; } if ($response['stat']!=200) { error_log1('failed to get siteid. response' . json_encode($response)); $response['body'] .= '\nfailed to get siteid.'; return $response; //throw new Exception($response['stat'].', failed to get siteid.'.$response['body']); } return json_decode($response['body'],true)['id']; } public function del_upload_cache($path) { error_log1('del.tmp:GET,'.json_encode($_GET,JSON_PRETTY_PRINT)); $tmp = splitlast($_GET['filename'], '/'); if ($tmp[1]!='') { $filename = $tmp[0] . '/.' . $_GET['filelastModified'] . '_' . $_GET['filesize'] . '_' . $tmp[1] . '.tmp'; } else { $filename = '.' . $_GET['filelastModified'] . '_' . $_GET['filesize'] . '_' . $_GET['filename'] . '.tmp'; } $filename = path_format( path_format($_SERVER['list_path'] . path_format($path)) . '/' . spurlencode($filename, '/') ); $tmp = $this->MSAPI('DELETE', $filename, ''); $path1 = path_format($_SERVER['list_path'] . path_format($path)); if ($path1!='/'&&substr($path1,-1)=='/') $path1=substr($path1,0,-1); savecache('path_' . $path1, json_decode('{}',true), $this->disktag, 1); return output($tmp['body'],$tmp['stat']); } public function get_thumbnails_url($path = '/') { $thumb_url = getcache('thumb_'.$path, $this->disktag); if ($thumb_url=='') { $url = $this->api_url . $this->ext_api_url; if ($path !== '/') { $url .= ':' . $path; if (substr($url,-1)=='/') $url=substr($url,0,-1); } $url .= ':/thumbnails/0/medium'; $files = json_decode(curl('GET', $url, false, ['Authorization' => 'Bearer ' . $this->access_token])['body'], true); if (isset($files['url'])) { savecache('thumb_' . $path, $files['url'], $this->disktag); $thumb_url = $files['url']; } } return $thumb_url; } public function bigfileupload($path) { if ($_POST['upbigfilename']=='') return output('error: no file name', 400); if (!is_numeric($_POST['filesize'])) return output('error: no file size', 400); if (!$_SERVER['admin']) if (!isset($_POST['filemd5'])) return output('error: no file md5', 400); $tmp = splitlast($_POST['upbigfilename'], '/'); if ($tmp[1]!='') { $fileinfo['name'] = $tmp[1]; if ($_SERVER['admin']) $fileinfo['path'] = $tmp[0]; } else { $fileinfo['name'] = $_POST['upbigfilename']; } $fileinfo['size'] = $_POST['filesize']; $fileinfo['filelastModified'] = $_POST['filelastModified']; if ($_SERVER['admin']) { $filename = spurlencode($_POST['upbigfilename'], '/'); } else { $tmp1 = splitlast($fileinfo['name'], '.'); if ($tmp1[0]==''||$tmp1[1]=='') $filename = $_POST['filemd5']; else $filename = $_POST['filemd5'] . '.' . $tmp1[1]; } if ($fileinfo['size']>10*1024*1024) { $cachefilename = spurlencode( $fileinfo['path'] . '/.' . $fileinfo['filelastModified'] . '_' . $fileinfo['size'] . '_' . $fileinfo['name'] . '.tmp', '/'); $getoldupinfo=$this->list_files(path_format($path . '/' . $cachefilename)); //echo json_encode($getoldupinfo, JSON_PRETTY_PRINT); if (isset($getoldupinfo['file'])&&$getoldupinfo['size']<5120) { $getoldupinfo_j = curl('GET', $getoldupinfo['url']); $getoldupinfo = json_decode($getoldupinfo_j['body'], true); if ( json_decode( curl('GET', $getoldupinfo['uploadUrl'])['body'], true)['@odata.context']!='' ) return output($getoldupinfo_j['body'], $getoldupinfo_j['stat']); } } $response = $this->MSAPI('createUploadSession', path_format($path . '/' . $filename), '{"item": { "@microsoft.graph.conflictBehavior": "fail" }}'); if ($response['stat']<500) { $responsearry = json_decode($response['body'],true); if (isset($responsearry['error'])) return output($response['body'], $response['stat']); $fileinfo['uploadUrl'] = $responsearry['uploadUrl']; if ($fileinfo['size']>10*1024*1024) $this->MSAPI('PUT', path_format($path . '/' . $cachefilename), json_encode($fileinfo, JSON_PRETTY_PRINT)); } return output($response['body'], $response['stat']); } protected function MSAPI($method, $path, $data = '') { $activeLimit = getConfig('activeLimit', $this->disktag); if ($activeLimit!='') { if ($activeLimit>time()) { $tmp['error']['code'] = 'Retry-After'; $tmp['error']['message'] = 'MS limit until ' . date('Y-m-d H:i:s', $activeLimit); return [ 'stat' => 429, 'body' => json_encode($tmp) ]; } else { setConfig(['activeLimit' => ''], $this->disktag); } } if (substr($path,0,7) == 'http://' or substr($path,0,8) == 'https://') { $url = $path; } else { $url = $this->api_url . $this->ext_api_url; if ($path=='' or $path=='/') { $url .= '/'; } else { $url .= ':' . $path; if (substr($url,-1)=='/') $url=substr($url,0,-1); } if ($method=='PUT') { if ($path=='' or $path=='/') { $url .= 'content'; } else { $url .= ':/content'; } $headers['Content-Type'] = 'text/plain'; } elseif ($method=='PATCH') { $headers['Content-Type'] = 'application/json'; } elseif ($method=='POST') { $headers['Content-Type'] = 'application/json'; } elseif ($method=='DELETE') { $headers['Content-Type'] = 'application/json'; } else { if ($path=='' or $path=='/') { $url .= $method; } else { $url .= ':/' . $method; } $method='POST'; $headers['Content-Type'] = 'application/json'; } } $headers['Authorization'] = 'Bearer ' . $this->access_token; if (!isset($headers['Accept'])) $headers['Accept'] = '*/*'; //if (!isset($headers['Referer'])) $headers['Referer'] = $url;* $sendHeaders = array(); foreach ($headers as $headerName => $headerVal) { $sendHeaders[] = $headerName . ': ' . $headerVal; } $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_CUSTOMREQUEST, $method); curl_setopt($ch, CURLOPT_POSTFIELDS, $data); curl_setopt($ch, CURLOPT_TIMEOUT, 5); curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 10); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_HEADER, 0); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0); curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0); //curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1); curl_setopt($ch, CURLOPT_HTTPHEADER, $sendHeaders); $retry = 0; $response = []; while ($retry<3&&!$response['stat']) { $response['body'] = curl_exec($ch); $response['stat'] = curl_getinfo($ch, CURLINFO_HTTP_CODE); $retry++; } //$response['Location'] = curl_getinfo($ch); if ($response['stat']==429) { $res = json_decode($response['body'], true); $retryAfter = $res['error']['retryAfterSeconds']; setConfig(['activeLimit' => time()+$retryAfter], $this->disktag); } curl_close($ch); error_log1($response['stat'].' '.$response['body'].' '.$url.' '); return $response; } }